OpenCV cvDFT 傅里叶变换

【原文:http://blog.csdn.net/u013777833/article/details/19926191】

[cpp]  view plain copy
  1. #include<cv.h>  
  2. #include<highgui.h>  
  3. #include<stdio.h>  
  4.   
  5. void fft2shift(IplImage *src, IplImage *dst)  
  6. {  
  7.     IplImage *image_Re = 0, *image_Im = 0;  
  8.     int nRow, nCol, i, j, cy, cx;  
  9.     double scale, shift, tmp13, tmp24;  
  10.     image_Re = cvCreateImage(cvGetSize(src), IPL_DEPTH_64F, 1);  
  11.     //Imaginary part  
  12.     image_Im = cvCreateImage(cvGetSize(src), IPL_DEPTH_64F, 1);  
  13.     cvSplit( src, image_Re, image_Im, 0, 0 );  
  14.     //具体原理见冈萨雷斯数字图像处理p123  
  15.     // Compute the magnitude of the spectrum Mag = sqrt(Re^2 + Im^2)  
  16.     //计算傅里叶谱  
  17.     cvPow( image_Re, image_Re, 2.0);  
  18.     cvPow( image_Im, image_Im, 2.0);  
  19.     cvAdd( image_Re, image_Im, image_Re);  
  20.     cvPow( image_Re, image_Re, 0.5 );  
  21.     //对数变换以增强灰度级细节(这种变换使以窄带低灰度输入图像值映射  
  22.     //一宽带输出值,具体可见冈萨雷斯数字图像处理p62)  
  23.     // Compute log(1 + Mag);  
  24.     cvAddS( image_Re, cvScalar(1.0), image_Re ); // 1 + Mag  
  25.     cvLog( image_Re, image_Re ); // log(1 + Mag)  
  26.   
  27.     //Rearrange the quadrants of Fourier image so that the origin is at the image center  
  28.     nRow = src->height;  
  29.     nCol = src->width;  
  30.     cy = nRow/2; // image center  
  31.     cx = nCol/2;  
  32.     //CV_IMAGE_ELEM为OpenCV定义的宏,用来读取图像的像素值,这一部分就是进行中心变换  
  33.     for( j = 0; j < cy; j++ ){  
  34.         for( i = 0; i < cx; i++ ){  
  35.             //中心化,将整体份成四块进行对角交换  
  36.             tmp13 = CV_IMAGE_ELEM( image_Re, double, j, i);  
  37.             CV_IMAGE_ELEM( image_Re, double, j, i) = CV_IMAGE_ELEM(  
  38.                 image_Re, double, j+cy, i+cx);  
  39.             CV_IMAGE_ELEM( image_Re, double, j+cy, i+cx) = tmp13;  
  40.   
  41.             tmp24 = CV_IMAGE_ELEM( image_Re, double, j, i+cx);  
  42.             CV_IMAGE_ELEM( image_Re, double, j, i+cx) =  
  43.                 CV_IMAGE_ELEM( image_Re, double, j+cy, i);  
  44.             CV_IMAGE_ELEM( image_Re, double, j+cy, i) = tmp24;  
  45.         }  
  46.     }  
  47.     //归一化处理将矩阵的元素值归一为[0,255]  
  48.     //[(f(x,y)-minVal)/(maxVal-minVal)]*255  
  49.     double minVal = 0, maxVal = 0;  
  50.     // Localize minimum and maximum values  
  51.     cvMinMaxLoc( image_Re, &minVal, &maxVal );  
  52.     // Normalize image (0 - 255) to be observed as an u8 image  
  53.     scale = 255/(maxVal - minVal);  
  54.     shift = -minVal * scale;  
  55.     cvConvertScale(image_Re, dst, scale, shift);  
  56.     cvReleaseImage(&image_Re);  
  57.     cvReleaseImage(&image_Im);  
  58. }  
  59. int main(int argc, char* argv[])  
  60. {  
  61.     IplImage *src ,*dst,*Invdst,*temp,*Im = 0,*Re,*FourierImage;  
  62.       
  63.     temp = cvLoadImage("C:\\Users\\Lonely\\Desktop\\lena.jpg",0);  
  64.     //显示原图像  
  65.     cvNamedWindow("待变换图像",0);  
  66.     cvShowImage("待变换图像",temp);  
  67.     dst = cvCreateImage(cvGetSize(temp),temp->depth,1);  
  68.     FourierImage = cvCreateImage(cvGetSize(temp),temp->depth,1);  
  69.     Invdst = cvCreateImage(cvGetSize(temp),temp->depth,1);  
  70.     src = cvCreateImage(cvGetSize(temp),IPL_DEPTH_64F,2);  
  71.     Im = cvCreateImage(cvGetSize(temp),IPL_DEPTH_64F,1);  
  72.     Re = cvCreateImage(cvGetSize(temp),IPL_DEPTH_64F,1);  
  73.       
  74.     //利用cvConcertScale转换数据类型  
  75.     cvConvertScale(temp,Re);  
  76.     //复数通道的灰度值设为0  
  77.     cvZero(Im);  
  78.     //傅里叶变换在复数域,在opencv中表示为二通道  
  79.   
  80.     cvMerge(Re,Im,NULL,NULL,src);  
  81.     IplImage *Fourier = cvCreateImage(cvGetSize(temp),IPL_DEPTH_64F,2);  
  82.     IplImage *InvFourier = cvCreateImage(cvGetSize(temp),IPL_DEPTH_64F,2);  
  83.   
  84.     //傅里叶变换  
  85.     cvDFT(src,Fourier,CV_DXT_FORWARD);  
  86.     cvDFT(Fourier,InvFourier,CV_DXT_INV_SCALE);  
  87.     cvSplit(Fourier,Re,Im,NULL,NULL);  
  88.     //利用cvConcertScale转换数据类型  
  89.     cvConvertScale(Re,dst);  
  90.   
  91.   
  92.     //显示傅里叶变换图像  
  93.     cvNamedWindow("傅里叶变换图像",0);  
  94.     cvShowImage("傅里叶变换图像",dst);  
  95.   
  96.    //中心化  
  97.     fft2shift(Fourier,FourierImage);  
  98.     cvNamedWindow("中心化傅里叶变换图像",0);  
  99.     cvShowImage("中心化傅里叶变换图像",FourierImage);  
  100.   
  101.     cvSplit(InvFourier,Re,Im,NULL,NULL);  
  102.     //利用cvConcertScale转换数据类型  
  103.     cvConvertScale(Re,Invdst);  
  104.   
  105.     //显示傅里叶逆变换图像  
  106.     cvNamedWindow("傅里叶逆变换图像",0);  
  107.     cvShowImage("傅里叶逆变换图像",Invdst);  
  108.   
  109.     cvWaitKey(0);  
  110.   
  111.     //释放内存  
  112.     cvReleaseImage(&src);  
  113.     cvReleaseImage(&dst);  
  114.     cvReleaseImage(&Invdst);  
  115.     cvReleaseImage(&temp);  
  116.     cvReleaseImage(&Im);  
  117.     cvReleaseImage(&Re);  
  118.     cvReleaseImage(&Fourier);  
  119.     cvReleaseImage(&InvFourier);  
  120.   
  121.     cvDestroyAllWindows();  
  122.   
  123.   
  124.   
  125. }  

fft2shift来自http://blog.csdn.net/abcjennifer/article/details/7359952

结果:OpenCV cvDFT 傅里叶变换_第1张图片

OpenCV版本:2.4.4

更多 0


你可能感兴趣的:(dft)