www.pudn.com > FFT2Dsource.rar > PinYuLuBoDib.cpp


#include "stdafx.h" 
#include "windowsx.h" 
#include "math.h" 
#include "PinYuLuBoDib.h" 
#include "malloc.h" 
#include "MainFrm.h" 
#include "DSplitView.h" 
#include "Cdib.h" 
#define WIDTHBYTES(bits)    (((bits) + 31) / 32 * 4)  
 
 
#define SWAP(a,b) tempr=(a);(a)=(b);(b)=tempr 
#define pi 3.14159265359 
  
  
PinYuLuBoDib::PinYuLuBoDib() 
{ 
} 
PinYuLuBoDib::~PinYuLuBoDib() 
{ 
} 
 
CNumber PinYuLuBoDib::Add(CNumber c1,CNumber c2) 
{ 
	CNumber c; 
	c.re=c1.re+c2.re; 
	c.im=c1.im+c2.im; 
	return c; 
} 
CNumber PinYuLuBoDib::Sub(CNumber c1,CNumber c2) 
{ 
	CNumber c; 
	c.re=c1.re-c2.re; 
	c.im=c1.im-c2.im; 
	return c; 
} 
CNumber PinYuLuBoDib::Mul(CNumber c1,CNumber c2) 
{ 
	CNumber c; 
	c.re=c1.re*c2.re-c1.im*c2.im; 
	c.im=c1.re*c2.im+c2.re*c1.im; 
	return c; 
} 
 
/////////////////////////////////////////////////// 
//此函数实现快速傅立叶变换 
//参数t、f分别是指向时域和频域的指针,power是2的幂数 
/////////////////////////////////////////////////// 
void PinYuLuBoDib::QFC(CNumber* t,CNumber* f,int power) 
{ 
	long count;//傅立叶变换点数 
	int i,j,k,p,bfsize; 
	CNumber *w,*x,*a,*b;//复数结构类型的指针变量,其中w指向加权系数 
	double angle;//计算加权系数所用的角度值 
	count=1<byBitCount==8)	//灰度图像 
		   p_data=this->GetData();//指向原图象数据区 
	else	//24位真彩色 
		   p_data=this->GetData2(); 
	width=this->GetWidth();//得到图象宽度 
	height=this->GetHeight();//得到图象高度 
    long lLineBytes=WIDTHBYTES(width*8);//计算图象每行的字节数 
	while(w*2<=width)//计算进行傅立叶变换的宽度(2的整数次方) 
	{ 
		w*=2; 
		wp++; 
	} 
	while(h*2<=height)//计算进行傅立叶变换的高度(2的整数次方) 
	{ 
		h*=2; 
		hp++; 
	} 
	t=new CNumber[w*h];//分配存储器空间 
	f=new CNumber[w*h]; 
	for(j=0;j255) 
				temp=255; 
			 
			p=p_data+lLineBytes*(height-(jbyBitCount==8)//灰度图像 
		   p_data=this->GetData();//指向原图象数据区 
	else//24位真彩色 
		   p_data=this->GetData2(); 
	width=this->GetWidth();//得到图象宽度 
	height=this->GetHeight();//得到图象高度 
    long lLineBytes=WIDTHBYTES(width*8);//计算图象每行的字节数 
	while(w*2<=width)//计算进行傅立叶变换的宽度(2的整数次方) 
	{ 
		w*=2; 
		wp++; 
	} 
	while(h*2<=height)//计算进行傅立叶变换的高度(2的整数次方) 
	{ 
		h*=2; 
		hp++; 
	} 
	t=new CNumber[w*h];//分配存储器空间 
	f=new CNumber[w*h]; 
	for(j=0;j255) 
				temp=255; 
			p=p_data+lLineBytes*(height-(j=1;idim--)  
	{ 
		n=nn[idim]; 
		nrem=ntot/(n*nprev); 
		ip1=nprev << 1; 
		ip2=ip1*n; 
		ip3=ip2*nrem; 
		i2rev=1; 
		for (i2=1;i2<=ip2;i2+=ip1) 
		{ 
			if (i2 < i2rev)  
			{ 
				for (i1=i2;i1<=i2+ip1-2;i1+=2)  
				{ 
					for (i3=i1;i3<=ip3;i3+=ip2) 
					{ 
						i3rev=i2rev+i3-i2; 
						SWAP(data[i3],data[i3rev]); 
						SWAP(data[i3+1],data[i3rev+1]); 
					} 
				} 
			} 
			ibit=ip2 >> 1; 
			while (ibit >= ip1 && i2rev > ibit) 
			{ 
				i2rev -= ibit; 
				ibit >>= 1; 
			} 
			i2rev += ibit; 
		} 
		ifp1=ip1; 
		while (ifp1 < ip2)  
		{ 
			ifp2=ifp1 << 1; 
			theta=isign*pi*2/(ifp2/ip1); 
			wtemp=sin(0.5*theta); 
			wpr = -2.0*wtemp*wtemp; 
			wpi=sin(theta); 
			wr=1.0; 
			wi=0.0; 
			for (i3=1;i3<=ifp1;i3+=ip1) 
			{ 
				for (i1=i3;i1<=i3+ip1-2;i1+=2)  
				{ 
					for (i2=i1;i2<=ip3;i2+=ifp2)  
					{ 
						k1=i2; 
						k2=k1+ifp1; 
						tempr=wr*data[k2]-wi*data[k2+1]; 
						tempi=wr*data[k2+1]+wi*data[k2]; 
						data[k2]=data[k1]-tempr; 
						data[k2+1]=data[k1+1]-tempi; 
						data[k1] += tempr; 
						data[k1+1] += tempi; 
					} 
				} 
				wr=(wtemp=wr)*wpr-wi*wpi+wr; 
				wi=wi*wpr+wtemp*wpi+wi; 
			} 
			ifp1=ifp2; 
		} 
		nprev *= n; 
	} 
} 
 
/************************************************************************* 
* 函数:BWFilterL(int u,int v,int u1,int v1) 
*参数:u、v分别是截止频率的x、y分量值,由用户给定 
*功能:此函数用来实现图象的布特沃斯低通滤波 
/*************************************************************************/ 
 
void PinYuLuBoDib::BWFilterL(int u,int v,int n) 
{ 
	LPBYTE  p_data, p;//指向原图象数据区指针 
	int width,height;//原图象的宽度和高度        
	int i,j; 
	double max=0.0,d0,d;//中间变量 
	double *t,*H; 
	if(this->byBitCount==8)//灰度图像 
		   p_data=this->GetData();//指向原图象数据区 
	else//24位真彩色 
		   p_data=this->GetData2();//指向原图象数据区 
	width=this->GetWidth();//得到图象宽度 
	height=this->GetHeight();//得到图象高度 
    long lLineBytes=WIDTHBYTES(width*8);//计算图象每行的字节数 
	t=new double [height*lLineBytes*2+1];//分配存储器空间 
	H=new double [height*lLineBytes*2+1]; 
	d0=sqrt(u*u+v*v);//计算截止频率d0 
	for(j=0;jbyBitCount==8)//灰度图像 
		   p_data=this->GetData();//指向原图象数据区 
	else//24位真彩色 
		   p_data=this->GetData2();//指向原图象数据区 
	width=this->GetWidth();//得到图象宽度 
	height=this->GetHeight();//得到图象高度 
    long lLineBytes=WIDTHBYTES(width*8);//计算图象每行的字节数 
	t=new double [height*lLineBytes*2+1];//分配存储器空间 
	H=new double [height*lLineBytes*2+1]; 
	d0=sqrt(u*u+v*v);//计算截止频率d0 
	for(j=0;jbyBitCount==8)//灰度图像 
		p_data=this->GetData();//指向原图象数据区 
	else//24位真彩色 
		p_data=this->GetData2();//指向原图象数据区 
	width=this->GetWidth();//得到图象宽度 
	height=this->GetHeight();//得到图象高度 
    long lLineBytes=WIDTHBYTES(width*8);//计算图象每行的字节数 
	t=new double [height*lLineBytes*2+1];//分配存储器空间 
	H=new double [height*lLineBytes*2+1]; 
	d0=sqrt(u*u+v*v);//计算截止频率d0 
	for(j=0;jbyBitCount==8)//灰度图像 
		p_data=this->GetData();//指向原图象数据区 
	else//24位真彩色 
		p_data=this->GetData2();//指向原图象数据区 
	width=this->GetWidth();//得到图象宽度 
	height=this->GetHeight();//得到图象高度 
    long lLineBytes=WIDTHBYTES(width*8);//计算图象每行的字节数 
	t=new double [height*lLineBytes*2+1];//分配存储器空间 
	H=new double [height*lLineBytes*2+1]; 
	d0=sqrt(u*u+v*v);//计算截止频率d0 
	for(j=0;jbyBitCount==8)//灰度图像 
		   p_data=this->GetData();//指向原图象数据区 
	else//24位真彩色 
		   p_data=this->GetData2();//指向原图象数据区 
	width=this->GetWidth();//得到图象宽度 
	height=this->GetHeight();//得到图象高度 
    long lLineBytes=WIDTHBYTES(width*8);//计算图象每行的字节数 
	t=new double [height*lLineBytes*2+1];//分配存储器空间 
	H=new double [height*lLineBytes*2+1]; 
	d0=sqrt(u*u+v*v);//计算截止频率d0 
	d1=sqrt(u1*u1+v1*v1); 
	for(j=0;jd1) 
			{ 
				H[2*i+(2*lLineBytes)*j+1]=0.0; 
				H[2*i+(2*lLineBytes)*j+2]=0.0; 
			} 
			else 
			{ 
				H[2*i+(2*lLineBytes)*j+1]=(d-d1)/(d0-d1); 
				H[2*i+(2*lLineBytes)*j+2]=0.0; 
			}				 
		} 
	} 
    fourier(t,height,lLineBytes,1); 
	for(j=1;jbyBitCount==8)//灰度图像 
		p_data=this->GetData();//指向原图象数据区 
	else//24位真彩色 
		p_data=this->GetData2();//指向原图象数据区 
	width=this->GetWidth();//得到图象宽度 
	height=this->GetHeight();//得到图象高度 
    long lLineBytes=WIDTHBYTES(width*8);//计算图象每行的字节数 
	t=new double [height*lLineBytes*2+1];//分配存储器空间 
	H=new double [height*lLineBytes*2+1]; 
	d0=sqrt(u*u+v*v);//计算截止频率d0 
	d1=sqrt(u1*u1+v1*v1); 
	for(j=0;jd1) 
			{ 
				H[2*i+(2*lLineBytes)*j+1]=1; 
				H[2*i+(2*lLineBytes)*j+2]=0.0; 
			} 
			else 
			{ 
				H[2*i+(2*lLineBytes)*j+1]=(d-d0)/(d1-d0); 
				H[2*i+(2*lLineBytes)*j+2]=0.0; 
			}						 
		} 
	} 
    fourier(t,height,lLineBytes,1); 
	for(j=1;jbyBitCount==8)//灰度图像 
		p_data=this->GetData();//指向原图象数据区 
	else//24位真彩色 
		p_data=this->GetData2();//指向原图象数据区 
	width=this->GetWidth();//得到图象宽度 
	height=this->GetHeight();//得到图象高度 
    long lLineBytes=WIDTHBYTES(width*8);//计算图象每行的字节数 
	t=new double [height*lLineBytes*2+1];//分配存储器空间 
	H=new double [height*lLineBytes*2+1]; 
	d0=sqrt(u*u+v*v);//计算截止频率d0 
	for(j=0;jbyBitCount==8)//灰度图像 
		p_data=this->GetData();//指向原图象数据区 
	else//24位真彩色 
		p_data=this->GetData2();//指向原图象数据区 
	width=this->GetWidth();//得到图象宽度 
	height=this->GetHeight();//得到图象高度 
    long lLineBytes=WIDTHBYTES(width*8);//计算图象每行的字节数 
	t=new double [height*lLineBytes*2+1];//分配存储器空间 
	H=new double [height*lLineBytes*2+1]; 
	d0=sqrt(u*u+v*v);//计算截止频率d0 
	for(j=0;j