Programming Skills-table-driven programming
<Span style = "font-family: verdana, geneva; font-size: 15px;">/* Image format-dependent operations. */typedef struct {jas_image_t * (* decode) (jas_stream_t * in, char * opts);/* Decode image data from a stream. */int (* encode) (jas_image_t * image, jas_stream_t * out, char * opts);/* Encode image data to a stream. */int (* validate) (jas_stream_t * in);/* Determine if stream data is in a particle form At. */} jas_image_fmtops_t;/* Image format information. */typedef struct {int id;/* The ID for this format. */char * name;/* The name by which this format is identified. */char * ext;/* The file name extension associated with this format. */char * desc;/* A brief description of the format. */jas_image_fmtops_t ops;/* The operations for this format. */} jas_image_fmtinfo_t; </span> the code is from The jas_image_fmtops_t struct, extracted from the source code of jasper, defines three function pointers, which are basic operations on images. S_image_fmtinfo_t describes the most basic attributes of an image. Including the ID and format definition. At the beginning, I didn't understand why I defined the id as an enumeration type instead of an int. When I see the following code, I know. Let's take a look at the following code jas_init <span style = "font-size: 15px; font-family: verdana, geneva;">/* Initialize the image format table. */int jas_init () {jas_image_fmtops_t fmtops; int fmtid; fmtid = 0; # if! Defined (EXCLUDE_MIF_SUPPORT) fmtops. decode = mif_decode; fmtops. encode = mif_encode; fmtops. validate = mif_validate; jas_image_addfmt (fmtid, "mif", "mif", "My Image Format (MIF)", & fmtops); ++ fmtid; # endif # if! Defined (EXCLUDE_PNM_SUPPORT) fmtops. decode = pnm_decode; fmtops. encode = pnm_encode; fmtops. validate = pnm_validate; jas_image_addfmt (fmtid, "pnm", "pnm", "Portable Graymap/Pixmap (PNM)", & fmtops); jas_image_addfmt (fmtid, "pnm ", "pgm", "Portable Graymap/Pixmap (PNM)", & fmtops); jas_image_addfmt (fmtid, "pnm", "ppm", "Portable Graymap/Pixmap (PNM )", & fmtops); ++ fmtid; # endif # if! Defined (exclude_bmp _support) fmtops. decode = BMP _decode; fmtops. encode = BMP _ encode; fmtops. validate = bmp _validate; jas_image_addfmt (fmtid, "bmp", "BMP", "Microsoft Bitmap (bmp)", & fmtops); ++ fmtid; # endif # if! Defined (EXCLUDE_RAS_SUPPORT) fmtops. decode = ras_decode; fmtops. encode = ras_encode; fmtops. validate = ras_validate; jas_image_addfmt (fmtid, "ras", "ras", "Sun Rasterfile (RAS)", & fmtops); ++ fmtid; # endif # if! Defined (EXCLUDE_JP2_SUPPORT) fmtops. decode = jp2_decode; fmtops. encode = jp2_encode; fmtops. validate = jp2_validate; jas_image_addfmt (fmtid, "jp2", "jp2", "JPEG-2000 JP2 File Format Syntax (ISO/IEC 15444-1)", & fmtops); ++ fmtid; fmtops. decode = jpc_decode; fmtops. encode = jpc_encode; fmtops. validate = jpc_validate; jas_image_addfmt (fmtid, "jpc", "jpc", "JPEG-2000 Code Stream Syntax (ISO/IEC 15444-1) ", & Fmtops); ++ fmtid; # endif # if! Defined (EXCLUDE_JPG_SUPPORT) fmtops. decode = jpg_decode; fmtops. encode = jpg_encode; fmtops. validate = jpg_validate; jas_image_addfmt (fmtid, "jpg", "jpg", "JPEG (ISO/IEC 10918-1)", & fmtops); ++ fmtid; # endif # if! Defined (EXCLUDE_PGX_SUPPORT) fmtops. decode = pgx_decode; fmtops. encode = pgx_encode; fmtops. validate = pgx_validate; jas_image_addfmt (fmtid, "pgx", "pgx", "JPEG-2000 VM Format (PGX)", & fmtops); ++ fmtid; # endif/* We must not register the JasPer library exit handler until after at least one memory allocation is already med. this is desirable as it ensures that the JasPer exit handler is called before t He debug memory allocator exit handler. */atexit (jas_cleanup); return 0 ;}</span> <span style = "font-family: verdana, geneva; font-size: 15px; "> int jas_image_addfmt (int id, char * name, char * ext, char * desc, jas_image_fmtops_t * ops) {jas_image_fmtinfo_t * fmtinfo; assert (id> = 0 & name & ext & ops); if (jas_image_numfmts> = JAS_IMAGE_MAXFMTS) {return-1;} fmtinfo = & jas_image_fmtinfos [jas_image _ Numfmts]; fmtinfo-> id = id; if (! (Fmtinfo-> name = jas_strdup (name) {return-1;} if (! (Fmtinfo-> ext = jas_strdup (ext) {jas_free (fmtinfo-> name); return-1 ;}if (! (Fmtinfo-> desc = jas_strdup (desc) {jas_free (fmtinfo-> name); jas_free (fmtinfo-> ext); return-1 ;} fmtinfo-> ops = * ops; ++ jas_image_numfmts; return 0 ;}</span> jas_image_fmtinfos is an array of the jas_image_fmtinfo_t type. 1 <span style = "font-size: 15px; font-family: ;"> answer: </span> <br> <span style = "font-size: 15px; "> <span style =" font-family:; "> from the code above, we can see that the author uses table-driven programming. The global variable jas_image_fmtinfos stores all supported image formats. Each time you add or delete a format, you only need to modify the jas_init code, and the format number is dynamic. You can search for the array each time you use it. <Br> let's take a look at the code used. This function is numbered based on the suffix. <Br> </span> <span style = "font-family: ;"> int jas_image_fmtfromname (char * name) </span> <em id = "_ mceDel"> <span style = "font-family:; "> <br> </span> </em> </span> int jas_image_fmtfromname (char * name) {int I; char * ext; jas_image_fmtinfo_t * fmtinfo; /* Get the file name extension. */if (! (Ext = strrchr (name ,'. ') {return-1 ;}++ ext;/* Try to find a format that uses this extension. */for (I = 0, fmtinfo = jas_image_fmtinfos; I <jas_image_numfmts; ++ I, ++ fmtinfo) {/* Do we have a match? */If (! Strcmp (ext, fmtinfo-> ext) {return fmtinfo-> id;} return-1;} as shown in the code above, each time you query the format of the suffix, compare the current suffix name with the suffix name in the jas_image_fmtinfos array to determine the id, which is highly scalable. <Span style = "font-size: 15px; font-family: ;"> </span>