簡體   English   中英

如何將8位OpenCV IplImage *轉換為32位IplImage *?

[英]How to convert an 8-bit OpenCV IplImage* to a 32-bit IplImage*?

我需要將8位IplImage轉換為32位IplImage。 使用來自整個網絡的文檔,我嘗試了以下方法:

// general code
img2 = cvCreateImage(cvSize(img->width, img->height), 32, 3);
int height    = img->height;
int width     = img->width;
int channels  = img->nChannels;
int step1     = img->widthStep;
int step2     = img2->widthStep;
int depth1    = img->depth;
int depth2    = img2->depth;
uchar *data1   = (uchar *)img->imageData;
uchar *data2   = (uchar *)img2->imageData;

for(h=0;h<height;h++) for(w=0;w<width;w++) for(c=0;c<channels;c++) {
   // attempt code...
}

// attempt one
// result: white image, two red spots which appear in the original image too.
// this is the closest result, what's going wrong?!
// see: http://files.dazjorz.com/cache/conversion.png
((float*)data2+h*step2+w*channels+c)[0] = data1[h*step1+w*channels+c];

// attempt two
// when I change float to unsigned long in both previous examples, I get a black screen.

// attempt three
// result: seemingly random data to the top of the screen.
data2[h*step2+w*channels*3+c] = data1[h*step1+w*channels+c];
data2[h*step2+w*channels*3+c+1] = 0x00;
data2[h*step2+w*channels*3+c+2] = 0x00;

// and then some other things. Nothing did what I wanted. I couldn't get an output
// image which looked the same as the input image.

如你所見,我真的不知道自己在做什么。 我很想知道,但如果我能正確完成這項工作,我會更加喜歡它。 謝謝你的幫助!

您正在尋找的功能是cvConvertScale()。 它會自動為您進行任何類型轉換。 您只需要指定要縮放1/255(將范圍[0 ... 255]映射到[0 ... 1])。

例:

IplImage *im8 = cvLoadImage(argv[1]);
IplImage *im32 = cvCreateImage(cvSize(im8->width, im8->height), 32, 3);

cvConvertScale(im8, im32, 1/255.);

請注意1/255.的點1/255. - 強制雙師。 沒有它你會得到0的標度。

也許這個鏈接可以幫到你?

編輯響應OP和評論的第二次編輯

你有沒有嘗試過

float value = 0.5

代替

float value = 0x0000001;

我認為浮動顏色值的范圍從0.0到1.0,其中1.0是白色。

浮點顏色從0.0到1.0,uchars從0到255.以下代碼修復它:

// h is height, w is width, c is current channel (0 to 2)
int b = ((uchar *)(img->imageData + h*img->widthStep))[w*img->nChannels + c];
((float *)(img2->imageData + h*img2->widthStep))[w*img2->nChannels + c] = ((float)b) / 255.0;

很多,非常感謝Stefan Schmidt幫助我解決這個問題!

您可以使用boost :: shared_ptr和template-metaprogramming創建IplImage包裝器。 我已經做到了,我得到了自動垃圾收集,以及從一個深度到另一個深度的自動圖像轉換,或者從單通道到多通道圖像的自動圖像轉換。

我已經調用了API blImageAPI,它可以在這里找到: http//www.barbato.us/2010/10/14/image-data-structure-based-shared_ptr-iplimage/

它非常快,並且使代碼非常易讀(適用於維護算法)

它也可以在opencv算法中代替IplImage而不改變任何東西。

祝你好運,玩得開心!

如果你沒有放點(。),一些編譯器會理解為int除法,給你一個int結果(在這種情況下為零)。

IplImage * img8,* img32;
img8 = cvLoadImage(“a.jpg”,1);

    cvNamedWindow("Convert",1);
    img32 = cvCreateImage(cvGetSize(img8),IPL_DEPTH_32F,3);
    cvConvertScale(img8,img32,1.0/255.0,0.0);

//用於確認檢查像素值(介於0 - 1之間)

    for(int row = 0; row < img32->height; row++ ){
                float* pt = (float*) (img32->imageData + row * img32->widthStep);
                for ( int col = 0; col < width; col++ )
                            printf("\n %3.3f , %3.3f , %3.3f ",pt[3*col],pt[3*col+1],pt[3*col+2]);                  
            }

    cvShowImage("Convert",img32);
    cvWaitKey(0);
    cvReleaseImage(&img8);
    cvReleaseImage(&img32);
    cvDestroyWindow("Convert");

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM