1. C API
1.1. 起因
做生物图象处理, 先用python, 速度实在太慢, 用c 选图像库, ImageMagic看上去不错. 可惜, 文档实在太简洁了, 好在open source, 看着源码摸索着走.
1.2. 开端
ImageMagic的C API有两种, MagickWand 和 MagickCore , Manual两种API都有一个例子程序. MagickCore是一个低阶的API, 但是更灵活, 将仔细讨论. 读取图像, 计算RGB分量的联合分布R-G , G-B, B-R:
1 2 3 #include <stdio.h> 4 #include <stdlib.h> 5 #include <string.h> 6 #include <time.h> 7 #include <magick/ImageMagick.h> 8 9 int main(int argc,char **argv) 10 { 11 ExceptionInfo 12 exception; 13 14 Image 15 *image, 16 *rgimage, 17 *gbimage, 18 *brimage; 19 20 ImageInfo 21 *image_info; 22 char 23 * infilename, 24 * rgfilename, 25 * gbfilename, 26 * brfilename; 27 PixelPacket * ipix, *rgpix,*gbpix, *brpix; 28 29 unsigned char M[3][256*256]; 30 unsigned char r,g,b; 31 32 infilename = argv[1]; 33 rgfilename = argv[2]; 34 gbfilename = argv[3]; 35 brfilename = argv[4]; 36 37 int i,j; 38 39 /* 40 Initialize the image info structure and read an image. 41 */ 42 InitializeMagick(*argv); 43 GetExceptionInfo(&exception); 44 image_info=CloneImageInfo((ImageInfo *) NULL); 45 46 (void) strcpy(image_info->filename, infilename); 47 image=ReadImage(image_info,&exception); 48 if (exception.severity != UndefinedException) 49 CatchException(&exception); 50 if (image == (Image *) NULL) 51 exit(1); 52 /* 53 Turn the images into a thumbnail sequence. 54 */ 55 56 fprintf(stderr, "\nImage Info:\n" 57 "name: %s\n" 58 "colorspace : %d\n" 59 "type : %d\n" 60 "columns: %ld rows : %ld\n" 61 "depth: %ld colors: %ld\n" 62 , 63 image_info->filename, 64 image->colorspace, 65 GetImageType(image, &exception), 66 image->columns, 67 image->rows, 68 image->depth, 69 image->colors 70 ); 71 72 ipix = AcquireImagePixels(image, 0, 0, 73 image->columns ,image->rows, 74 &exception); 75 fprintf(stderr, "\ncounting ... \n"); 76 memset(M,0,sizeof(M)); 77 for(i=0; i < image->columns*image->rows ; i++) 78 { 79 r = ScaleQuantumToChar(ipix[i].red); 80 g = ScaleQuantumToChar(ipix[i].green); 81 b = ScaleQuantumToChar(ipix[i].blue); 82 //if(i%100<10) fprintf(stderr, "(%d,%d,%d)\n", r,g,b); 83 M[0][r*256 + g] < 255 ? M[0][r*256 + g] += 1:0; 84 M[1][g*256 + b] < 255 ? M[1][g*256 + b] += 1:0; 85 M[2][b*256 + r] < 255 ? M[2][b*256 + r] += 1:0; 86 } 87 88 fprintf(stderr, "Writeing file...\n"); 89 rgimage = ConstituteImage(256,256,"I",CharPixel,M[0],&exception); 90 gbimage = ConstituteImage(256,256,"I",CharPixel,M[1],&exception); 91 brimage = ConstituteImage(256,256,"I",CharPixel,M[2],&exception); 92 93 fprintf(stderr, "Writeing file: %s\n", rgfilename); 94 (void) strcpy(rgimage->filename, rgfilename); 95 WriteImage(image_info, rgimage); 96 fprintf(stderr, "Writeing file: %s\n", gbfilename); 97 (void) strcpy(gbimage->filename, gbfilename); 98 WriteImage(image_info, gbimage); 99 fprintf(stderr, "Writeing file: %s\n", brfilename); 100 (void) strcpy(brimage->filename, brfilename); 101 WriteImage(image_info, brimage); 102 103 image_info=DestroyImageInfo(image_info); 104 105 DestroyExceptionInfo(&exception); 106 DestroyMagick(); 107 return(0); 108 } 109
CC = gcc MFLAGS = `Wand-config --cflags --cppflags` MLIBS = `Wand-config --ldflags --libs` all: wand core wand: wand.c $(CC) $(MFLAGS) wand.c $(MLIBS) -o wand core: core.c $(CC) $(MFLAGS) wand.c $(MLIBS) -o core mf: $(CFILE).c # if $CFILE then $(CC) $(MFLAGS) $(CFILE).c $(MLIBS) -o $(CFILE) rimg: rimg.c $(CC) $(MFLAGS) rimg.c $(MLIBS) -o rimg run-rimg: rimg ./rimg t1.png rg1.png gb1.png br1.png ./rimg t2.png rg2.png gb2.png br2.png ./rimg t3.png rg3.png gb3.png br3.png