声振论坛

 找回密码
 我要加入

QQ登录

只需一步,快速开始

查看: 4393|回复: 5

[C/C++] C++语言的复数与矩阵运算库

[复制链接]
发表于 2006-10-10 00:35 | 显示全部楼层 |阅读模式

马上注册,结交更多好友,享用更多功能,让你轻松玩转社区。

您需要 登录 才可以下载或查看,没有账号?我要加入

x
总共包含三个文件:
COMPLEX.H
matrix.h
text.cpp
本程序打包下载见本贴4楼


COMPLEX.H如下:
  1. /* -------------------------------------------------------------------- */
  2. /* Z++ Version 1.10               complex.h       Last revised 10/10/92 */
  3. /*                                                                      */
  4. /* Complex number class for Turbo C++/Borland C++.                      */
  5. /* Copyright 1992 by Carl W. Moreland                                   */
  6. /* -------------------------------------------------------------------- */

  7. #ifndef COMPLEXdotH
  8. #define COMPLEXdotH

  9. #include <math.h>
  10. #include <iostream.h>

  11. const unsigned char Z_RADIANS = 0;
  12. const unsigned char Z_DEGREES = 1;
  13. const unsigned char Z_COMMA   = 0;        // (x, y)
  14. const unsigned char Z_LETTER  = 1;        // x + iy

  15. class complex
  16. {
  17. public:
  18.   double re, im;

  19. private:
  20.   static unsigned char zArgMode;
  21.   static unsigned char zPrintMode;
  22.   static unsigned char zLetter;

  23. public:
  24.   complex(void): re(0), im(0) {}
  25.   complex(const double real, const double imag=0): re(real), im(imag) {}
  26.   complex(const complex& z): re(z.re), im(z.im) {}

  27.   friend double    re(const complex& z) {        // real part
  28.     return z.re;
  29.   }
  30.   friend double    im(const complex& z) {        // imaginary part
  31.     return z.im;
  32.   }
  33.   friend double  real(const complex& z) {        // real part
  34.     return z.re;
  35.   }
  36.   friend double  imag(const complex& z) {        // imaginary part
  37.     return z.im;
  38.   }
  39.   friend double   mag(const complex& z) {        // magnitude |z|
  40.     return sqrt(z.re*z.re + z.im*z.im);
  41.   }
  42.   friend double   arg(const complex& z);        // argument
  43.   friend double   ang(const complex& z) {        // angle
  44.     return arg(z);
  45.   }
  46.   friend double    ph(const complex& z) {        // phase
  47.     return arg(z);
  48.   }
  49.   friend complex conj(const complex& z) {        // complex conjugate
  50.     return complex(z.re, -z.im);
  51.   }
  52.   friend double  norm(const complex& z) {        // norm
  53.     return z.re*z.re + z.im*z.im;
  54.   }

  55.   friend complex rtop(double x,   double y=0);
  56.   friend complex ptor(double mag, double angle=0);
  57.   complex& topolar(void);
  58.   complex& torect(void);

  59.   void operator = (const complex& z) {                // z1 = z2
  60.     re = z.re;
  61.     im = z.im;
  62.   }
  63.   complex& operator += (const complex& z) {        // z1 += z2
  64.     re += z.re;
  65.     im += z.im;
  66.     return *this;
  67.   }
  68.   complex& operator -= (const complex& z) {        // z1 -= z2
  69.     re -= z.re;
  70.     im -= z.im;
  71.     return *this;
  72.   }
  73.   complex& operator *= (const complex& z) {        // z1 *= z2
  74.     *this = *this * z;
  75.     return *this;
  76.   }
  77.   complex& operator /= (const complex& z) {        // z1 /= z2
  78.     *this = *this / z;
  79.     return *this;
  80.   }
  81.   complex operator + (void) const {                // +z1
  82.     return *this;
  83.   }
  84.   complex operator - (void) const {                // -z1
  85.     return complex(-re, -im);
  86.   }

  87.   friend complex operator + (const complex& z1, const complex& z2) {
  88.     return complex(z1.re + z2.re, z1.im + z2.im);
  89.   }
  90.   friend complex operator + (const complex& z, const double x) {
  91.     return complex(z.re+x, z.im);
  92.   }
  93.   friend complex operator + (const double x, const complex& z) {
  94.     return complex(z.re+x, z.im);
  95.   }
  96.   friend complex operator - (const complex& z1, const complex& z2) {
  97.     return complex(z1.re - z2.re, z1.im - z2.im);
  98.   }
  99.   friend complex operator - (const complex&, const double);
  100.   friend complex operator - (const double x, const complex& z) {
  101.     return complex(x-z.re, -z.im);
  102.   }
  103.   friend complex operator * (const complex& z1, const complex& z2) {
  104.     double re = z1.re*z2.re - z1.im*z2.im;
  105.     double im = z1.re*z2.im + z1.im*z2.re;
  106.     return complex(re, im);
  107.   }
  108.   friend complex operator * (const complex& z, const double x) {
  109.     return complex(z.re*x, z.im*x);
  110.   }
  111.   friend complex operator * (const double x, const complex& z) {
  112.     return complex(z.re*x, z.im*x);
  113.   }
  114.   friend complex operator / (const complex&, const complex&);
  115.   friend complex operator / (const complex& z, const double x) {
  116.     return complex(z.re/x, z.im/x);
  117.   }
  118.   friend complex operator / (const double, const complex&);
  119.   friend complex operator ^ (const complex& z1, const complex& z2) {
  120.     return pow(z1, z2);
  121.   }

  122.   friend int operator == (const complex& z1, const complex& z2) {
  123.     return (z1.re == z2.re) && (z1.im == z2.im);
  124.   }
  125.   friend int operator != (const complex& z1, const complex& z2) {
  126.     return (z1.re != z2.re) || (z1.im != z2.im);
  127.   }

  128.   friend double   abs(const complex& z);
  129.   friend complex sqrt(const complex& z);
  130.   friend complex pow(const complex& base, const complex& exp);
  131.   friend complex pow(const complex& base, const double   exp);
  132.   friend complex pow(const double   base, const complex& exp);

  133.   friend complex   exp(const complex& z);
  134.   friend complex   log(const complex& z);
  135.   friend complex    ln(const complex& z);
  136.   friend complex log10(const complex& z);

  137.   friend complex  cos(const complex& z);
  138.   friend complex  sin(const complex& z);
  139.   friend complex  tan(const complex& z);

  140.   friend complex asin(const complex& z);
  141.   friend complex acos(const complex& z);
  142.   friend complex atan(const complex& z);

  143.   friend complex sinh(const complex& z);
  144.   friend complex cosh(const complex& z);
  145.   friend complex tanh(const complex& z);

  146.   void SetArgMode(unsigned char mode) const {
  147.     if(mode == Z_RADIANS || mode == Z_DEGREES)
  148.       zArgMode = mode;
  149.   }
  150.   void SetPrintMode(unsigned char mode) const {
  151.     if(mode == Z_COMMA || mode == Z_LETTER)
  152.       zPrintMode = mode;
  153.   }
  154.   void SetLetter(unsigned char letter) const {
  155.     zLetter = letter;
  156.   }

  157.   friend ostream& operator<<(ostream&, const complex&);
  158.   friend istream& operator>>(istream&, const complex&);
  159. };

  160. static const complex Z0(0, 0);                // complex number 0
  161. static const complex Z1(1, 0);                // complex number 1
  162. static const complex Zi(0, 1);                // complex number i
  163. static const complex Zinf(HUGE_VAL, HUGE_VAL); // complex number infinity
  164. static const complex Complex;

  165. /* -------------------------------------------------------------------- */
  166. /* Here is the same class with the name capitalized. If you prefer this */
  167. /* simply remove the comment delimiters below and comment out the 5     */
  168. /* static globals above.                                                */
  169. /* -------------------------------------------------------------------- */
  170. /*
  171. class Complex: public complex
  172. {
  173. public:
  174.   Complex(void): re(0), im(0) {}
  175.   Complex(const double real, const double imag=0): re(real), im(imag) {}
  176.   Complex(const complex& z): re(z.re), im(z.im) {}
  177. };

  178. static const Complex Z0(0, 0);                // complex number 0
  179. static const Complex Z1(1, 0);                // complex number 1
  180. static const Complex Zi(0, 1);                // complex number i
  181. static const Complex Zinf(HUGE_VAL, HUGE_VAL); // complex number infinity
  182. static const Complex complex;
  183. */

  184. #endif
复制代码

[ 本帖最后由 风花雪月 于 2006-10-10 00:44 编辑 ]
回复
分享到:

使用道具 举报

 楼主| 发表于 2006-10-10 00:41 | 显示全部楼层
matrix.h如下:
  1. #include "afxwin.h"
  2. #include "strstrea.h"
  3. #include "fstream.h"
  4. #include "iomanip.h"
  5. #include "stdlib.h"
  6. #include "malloc.h"
  7. #include "math.h"

  8. #define CDMatrix (CMatrix<double>)
  9. #define CIMatrix (CMatrix<int>)

  10. template<class Type>
  11. class CMatrix :public CObject
  12. {
  13.         protected:               
  14.                         Type    **f;
  15.                         int     row;
  16.                         int     col;
  17.         public:
  18.                 int  GetRow(){return row;}
  19.                 int  GetCol(){return col;}
  20.                 void SetRow(int r){row=r;}
  21.                 void SetCol(int l){col=l;}
  22.                 Type** GetF(){return f;}               
  23.                 CMatrix();
  24.                 CMatrix(int,int);
  25.                 CMatrix(CMatrix &copy);
  26.                 ~CMatrix();
  27.                 BOOL Ones(int);
  28.                 BOOL Ones(int,int);
  29.                 BOOL Zeros(int);
  30.                 BOOL Zeros(int,int);
  31.                 CMatrix Turn();
  32.                 CMatrix Inverse();
  33.                 CMatrix Construct(CMatrix &mat,CString style);
  34.                 CMatrix GetChild(int,int,int,int);
  35.                 BOOL Diag(Type *,int);
  36.                 BOOL Malloc(int,int);
  37.                 CMatrix   operator*(CMatrix  &m);
  38.                 friend CMatrix  operator*(double,CMatrix);
  39.                 friend CMatrix  operator*(CMatrix,double);
  40.                 CMatrix   operator/(Type x);
  41.                 CMatrix   operator+(CMatrix  &m);
  42.                 CMatrix   operator+(Type x);
  43.                 CMatrix   operator-(CMatrix  &m);
  44.                 CMatrix   operator-(Type x);
  45.                 CMatrix   operator-();
  46.                 Type* &operator[](int);
  47.                 friend istream  &operator>>(istream  &,CMatrix  &);
  48.                 friend ostream  &operator<<(ostream  &,CMatrix  &);
  49.                 void operator=(const CMatrix  &m);
  50.                 void operator=(Type);
  51.                 Type ** MatrixAlloc(int,int);
  52.                 void    MatrixFree(Type **);
  53.                 void    Hessenberg();
  54.                 BOOL    Cholesky();
  55.                 CMatrix QREigen(double,int);// return eigenvalue in two row matrix of a real matrix                
  56.                 CMatrix Jacobi(double eps,int jt);
  57. };

  58. template<class Type>
  59. Type* &CMatrix<Type>::operator[](int i)
  60. {
  61.         Type *tp;
  62.         tp=(Type *)f[i];
  63.         return tp;
  64. }
  65. template<class Type>
  66. CMatrix<Type>::CMatrix()
  67. {
  68.         f=NULL;
  69.         row=0;
  70.         col=0;
  71. }
  72. template<class Type>
  73. CMatrix<Type>::CMatrix(int m,int n)
  74. {       
  75.         f=MatrixAlloc(m,n);
  76.         row=m;
  77.         col=n;  
  78. }
  79. template<class Type>
  80. CMatrix<Type>::~CMatrix()
  81. {
  82.         if(f!=NULL) MatrixFree(f);
  83. }

  84. template<class Type>
  85. BOOL CMatrix<Type>::Ones(int m)
  86. {        
  87.         f=MatrixAlloc(m,m);
  88.         for(int i=0;i<m;i++)
  89.         for(int j=0;j<m;j++)
  90.         {
  91.                 if(i!=j)f[i][j]=0;
  92.                 else f[i][j]=1;
  93.         }
  94.         row=m;
  95.         col=m;
  96.         return TRUE;
  97. }
  98. template<class Type>
  99. BOOL CMatrix<Type>::Ones(int m,int n)
  100. {        
  101.         f=MatrixAlloc(m,n);
  102.         for(int i=0;i<m;i++)
  103.         for(int j=0;j<n;j++)
  104.         {
  105.                 f[i][j]=1;
  106.         }
  107.         row=m;
  108.         col=n;
  109.         return TRUE;
  110. }
  111. template<class Type>
  112. BOOL CMatrix<Type>::Zeros(int m)
  113. {        
  114.         f=MatrixAlloc(m,m);
  115.         for(int i=0;i<m;i++)
  116.         for(int j=0;j<m;j++)
  117.         {
  118.                 f[i][j]=0;
  119.         }
  120.         row=m;
  121.         col=m;
  122.         return TRUE;
  123. }
  124. template<class Type>
  125. BOOL CMatrix<Type>::Zeros(int m,int n)
  126. {        
  127.         f=MatrixAlloc(m,n);
  128.         if(f==NULL) return FALSE;
  129.         for(int i=0;i<m;i++)
  130.         for(int j=0;j<n;j++)
  131.         {
  132.                 f[i][j]=0;
  133.         }
  134.         row=m;
  135.         col=n;
  136.         return TRUE;
  137. }

  138. template<class Type>
  139. CMatrix<Type> CMatrix<Type>::operator*(CMatrix<Type>  &mat)
  140. {
  141.         int l,m,n;
  142.         l=GetRow();
  143.         m=GetCol();
  144.         n=mat.GetCol();
  145.         CMatrix tmp(l,n);
  146.         for(int k=0;k<l;k++)
  147.         for(int j=0;j<n;j++)
  148.         {
  149.                 for(int i=0;i<m;i++)
  150.                 tmp.f[k][j]+=f[k][i]*mat.f[i][j];
  151.         }       
  152.         return tmp;
  153. }

  154. template<class Type>
  155. CMatrix<Type> CMatrix<Type>::operator/(Type x)
  156. {
  157.         int l,n;
  158.         l=GetRow();
  159.         n=GetCol();
  160.         CMatrix<Type> tmp(l,n);
  161.         for(int j=0;j<l;j++)
  162.         for(int i=0;i<n;i++)
  163.                 tmp.f[j][i]=f[j][i]/x;
  164.         return tmp;
  165. }

  166. template<class Type>
  167. CMatrix<Type> CMatrix<Type>::operator+( CMatrix<Type>  &mat)
  168. {
  169.         int l1,m1;
  170.         l1=GetRow();
  171.         m1=GetCol();
  172.         CMatrix<Type> tmp(l1,m1);
  173.         for(int j=0;j<l1;j++)
  174.         for(int i=0;i<m1;i++)
  175.                 tmp.f[j][i]=f[j][i]+mat.f[j][i];
  176.         return tmp;
  177. }

  178. template<class Type>
  179. CMatrix<Type> CMatrix<Type>::operator+(Type x)
  180. {
  181.         int l,m;
  182.         l=GetRow();
  183.         m=GetCol();
  184.         CMatrix<Type> tmp(l,m);
  185.         for(int j=0;j<l;j++)
  186.         for(int i=0;i<m;i++)
  187.                 tmp.f[j][i]=f[j][i]+x;
  188.         return tmp;
  189. }

  190. template<class Type>
  191. CMatrix<Type> CMatrix<Type>::operator-(CMatrix<Type>  &mat)
  192. {
  193.         int l1,m1;
  194.         l1=GetRow();
  195.         m1=GetCol();
  196.         CMatrix<Type> tmp(l1,m1);
  197.         for(int j=0;j<l1;j++)
  198.         for(int i=0;i<m1;i++)
  199.                 tmp.f[j][i]=f[j][i]-mat.f[j][i];
  200.         return tmp;
  201. }
  202. template<class Type>
  203. CMatrix<Type> CMatrix<Type>::operator-()
  204. {
  205.         for(int i=0;i<row;i++)
  206.         for(int j=0;j<col;j++)
  207.                 f[i][j]=-f[i][j];
  208.         return *this;
  209. }       

  210. template<class Type>
  211. CMatrix<Type> CMatrix<Type>::operator-( Type x)
  212. {
  213.         int l,m;
  214.         l=GetRow();
  215.         m=GetCol();
  216.         CMatrix<Type> temp(l,m);
  217.         for(int j=0;j<l;j++)
  218.         for(int i=0;i<m;i++)
  219.                 temp.f[j][i]=f[j][i]-x;
  220.         return temp;
  221. }

  222. template<class Type>
  223. istream &operator>>(istream &in,CMatrix<Type> &mat)
  224. {   
  225.         int i,j;
  226.         for(i=0;i<mat.row;i++)
  227.         for(j=0;j<mat.col;j++)
  228.                  in>>mat.f[i][j];
  229.         cout<<endl;
  230.         return in;
  231. };

  232. template<class Type>
  233. ostream  & operator<<(ostream& out,CMatrix<Type> &v1)
  234. {
  235.         if(v1.GetF()==NULL)
  236.         {
  237.                 out<<"This Matrix cannot be output!";
  238.                 return out<<endl;
  239.         }
  240.         out<<setiosflags(ios::right||ios::fixed);
  241.         out<<setprecision(5);
  242.         out<<"["<<endl;
  243.         int mr=v1.GetRow();
  244.         int mc=v1.GetCol();
  245.         for(int j=0;j<mr;j++)
  246.         {
  247.                 for(int i=0;i<mc-1;i++)
  248.                         out<<setw(12)<<v1.f[j][i];
  249.                 out<<setw(12)<<v1.f[j][mc-1]<<";"<<endl;
  250.         }
  251.         return out<<"]"<<endl;
  252.        
  253. }
  254. template<class Type>
  255. CMatrix<Type>::CMatrix(CMatrix<Type> &copy)
  256. {
  257.         f=NULL;
  258.         *this=copy;
  259. }
  260.        
  261. template<class Type>
  262. void CMatrix<Type>::operator=(const CMatrix<Type> &copy)
  263. {
  264.        
  265.         if(this==&copy) return;
  266.         if(f!=NULL) MatrixFree(f);
  267.         int m,n;
  268.         m=copy.row;
  269.         n=copy.col;
  270.         f=MatrixAlloc(m,n);
  271.           for(int i=0;i<m;i++)
  272.         for(int j=0;j<n;j++)
  273.                 f[i][j]=copy.f[i][j];
  274.         row=m;
  275.         col=n;  
  276. }

  277. template<class Type>
  278. void CMatrix<Type>::operator=(Type d)
  279. {
  280.        
  281.         if(f==NULL)
  282.         {
  283.                 cout<<"The Matrix is not be allociated"<<endl;
  284.                 return;
  285.         }
  286.         for(int i=0;i<row;i++)
  287.         for(int j=0;j<col;j++)
  288.                 f[i][j]=d;
  289. }

  290. template<class Type>
  291. Type ** CMatrix<Type>::MatrixAlloc(int r,int c)
  292. {
  293.     Type *x,**y;
  294.     int   n;
  295.     x=(Type *)calloc(r*c,sizeof(Type));
  296.     y=(Type **)calloc(r,sizeof(Type *));
  297.         for(n=0;n<=r-1;++n)
  298.         y[n]=&x[c*n];
  299.         return(y);
  300. }

  301. template<class Type>
  302. void CMatrix<Type>::MatrixFree(Type **x)
  303. {
  304.    free(x[0]);
  305.    free(x);
  306. }
  307. template<class Type>
  308. BOOL CMatrix<Type>::Malloc(int m,int n)
  309. {
  310.         f=MatrixAlloc(m,n);
  311.         if(f==NULL) return FALSE;
  312.         row=m;
  313.         col=n;
  314.         return TRUE;
  315. }

  316.        
  317. template<class Type>
  318. CMatrix<Type> CMatrix<Type>::Turn()
  319. {
  320.         CMatrix<Type> tmp(col,row);
  321.         for(int i=0;i<row;i++)
  322.         for(int j=0;j<col;j++)
  323.                 tmp.f[j][i]=f[i][j];
  324.         return tmp;
  325. }

  326. template<class Type>
  327. BOOL CMatrix<Type>::Diag(Type *array,int m)
  328. {
  329.         f=MatrixAlloc(m,m);
  330.         for(int i=0;i<m;i++)
  331.         for(int j=0;j<m;j++)
  332.                 if(i==j) f[i][j]=array[i];
  333.         row=m;
  334.         col=m;
  335.         return TRUE;
  336. }

  337. template<class Type>
  338. CMatrix<Type> CMatrix<Type>::Construct(CMatrix<Type> &mat,CString style)
  339. {
  340.         int i,j;
  341.         CMatrix<Type> tmp;
  342.         if(style=="LR"||style=="lr")
  343.         {
  344.                 if(row!=mat.row)    return tmp;
  345.                 if(!tmp.Malloc(row,col+mat.col)) return tmp;
  346.                 for(i=0;i<tmp.row;i++)
  347.                 {
  348.                         for(j=0;j<tmp.col;j++)
  349.                         {
  350.                                 if(j<col) tmp.f[i][j]=f[i][j];
  351.                                 else      tmp.f[i][j]=mat.f[i][j-col];
  352.                         }
  353.                 }
  354.         }
  355.         return tmp;
  356. }

  357. template<class Type>       
  358. CMatrix<Type> CMatrix<Type>::GetChild(int sr,int sc,int er,int ec)
  359. {
  360.         int i,j;
  361.         CMatrix<Type> tmp(er-sr+1,ec-sc+1);
  362.         for(i=0;i<tmp.row;i++)
  363.         for(j=0;j<tmp.col;j++)
  364.                 tmp[i][j]=f[sr+i][sc+j];
  365.         return tmp;
  366. }
  367. template<class Type>       
  368. CMatrix<Type> CMatrix<Type>::Inverse()
  369. {  
  370.         Type d,p;
  371.     int *is,*js,i,j,k,v;
  372.     if(row!=col)  
  373.         {  
  374.                 cout<<"\nrow!=column,this matrix can't be inversed";
  375.                 return *this;   
  376.         }
  377.     is=new int[row];
  378.     js=new int[row];
  379.     for(k=0;k<=row-1;k++)
  380.         {
  381.                 d=0.0;
  382.             for(i=k;i<=row-1;i++)
  383.             for(j=k;j<=row-1;j++)
  384.             {  
  385.                         p=fabs(f[i][j]);
  386.                     if(p>d)
  387.                         {  
  388.                                 d=p;
  389.                                 is[k]=i;
  390.                                 js[k]=j;  
  391.                         }
  392.                 }
  393.             if(d+1.0==1.0)     //singular
  394.             {  
  395.                         delete is,js;
  396.                     cerr<<"\nerror*****not inv,be careful your matrix had been changed\n";
  397.                     return *this;   
  398.                 }
  399.             if(is[k]!=k)
  400.             for(j=0;j<=row-1;j++)
  401.                 {   
  402.                         v=is[k];
  403.                     p=f[k][j];
  404.                         f[k][j]=f[v][j];
  405.                         f[v][j]=p;
  406.                 }
  407.             if(js[k]!=k)
  408.             for(i=0;i<=row-1;i++)
  409.                 {  
  410.                         v=js[k];
  411.                     p=f[i][k];
  412.                         f[i][k]=f[i][v];
  413.                         f[i][v]=p;
  414.                 }
  415.             f[k][k]=1.0/f[k][k];
  416.             for(j=0;j<=row-1;j++)
  417.             if(j!=k)
  418.                f[k][j]*=f[k][k];
  419.             for(i=0;i<=row-1;i++)
  420.                         if(i!=k)
  421.                 for(j=0;j<=row-1;j++)
  422.                                 if(j!=k)
  423.                              f[i][j]-=f[i][k]*f[k][j];
  424.                 for(i=0;i<=row-1;i++)
  425.             if(i!=k)
  426.                          f[i][k]=-f[i][k]*f[k][k];
  427.         }
  428.     // change row and column after inverse
  429.         for(k=row-1;k>=0;k--)
  430.         {  
  431.                 if(js[k]!=k)
  432.                 for(j=0;j<=row-1;j++)
  433.                 {  
  434.                         v=js[k];
  435.                     p=f[k][j];
  436.                         f[k][j]=f[v][j];
  437.                         f[v][j]=p;
  438.                 }
  439.             if(is[k]!=k)
  440.                          for(i=0;i<=row-1;i++)
  441.                          {  
  442.                                  v=is[k];
  443.                                  p=f[i][k];  
  444.                                  f[i][k]=f[i][v];
  445.                                  f[i][v]=p;
  446.                      }
  447.       }
  448.         delete is,js;
  449.         return *this;   
  450. }

  451. template<class Type>       
  452. CMatrix<Type> operator * (double num,CMatrix<Type> right)
  453. {
  454.     CMatrix<Type> tmp(right.row,right.col);
  455.         int i,j;
  456.         for(i=0;i<right.row;i++)
  457.         for(j=0;j<right.col;j++)
  458.                  tmp.f[i][j]=num*right.f[i][j];
  459.         return tmp;
  460. }

  461. template<class Type>       
  462. CMatrix<Type> operator * (CMatrix<Type> left,double num)
  463. {   
  464.         CMatrix<Type> tmp(left.row,left.col);
  465.         int i,j;
  466.         for(i=0;i<left.row;i++)
  467.         for(j=0;j<left.col;j++)
  468.                  tmp.f[i][j]=num*left.f[i][j];
  469.         return tmp;
  470. }
  471. template<class Type>       
  472. void CMatrix<Type>::Hessenberg()
  473. {
  474.         int i,j,k;
  475.         double d,t;
  476.         if(row==0)
  477.         {
  478.             cerr<<"\na null matrix,can't use hessenberg transformation";
  479.             exit(1);
  480.          }
  481.         if(row!=col)
  482.         {
  483.             cerr<<"\nnot a square matrix,can't use hessenberg transformation";
  484.             exit(1);
  485.          }
  486.         for(k=1;k<=row-2;k++)
  487.         {
  488.             d=0.0;
  489.             for(j=k;j<=row-1;j++)
  490.             {
  491.                  t=f[j][k-1];
  492.                  if(fabs(t)>fabs(d))      { d=t;  i=j;  }
  493.              }
  494.             if(fabs(d)+1.0!=1.0)
  495.             {
  496.                  if(i!=k)
  497.                  {      for(j=k-1;j<=row-1;j++)
  498.                         {     t=f[i][j];  f[i][j]=f[k][j];  f[k][j]=t;
  499.                          }
  500.                         for(j=0;j<=row-1;j++)
  501.                         {      t=f[j][i];  f[j][i]=f[j][k];  f[j][k]=t;
  502.                          }
  503.                   }
  504.                  for(i=k+1;i<=row-1;i++)
  505.                  {       t=f[i][k-1]/d;
  506.                          f[i][k-1]=0.0;
  507.                          for(j=k;j<=row-1;j++)
  508.                          {      f[i][j]-=t*f[k][j];
  509.                           }
  510.                          for(j=0;j<=row-1;j++)
  511.                          {      f[j][k]+=t*f[j][i];
  512.                           }
  513.                   }
  514.              }
  515.         }
  516. }

  517. template<class Type>       
  518. BOOL CMatrix<Type>::Cholesky()
  519. {
  520.         int i,j,k;
  521.         double d;
  522.         if(row!=col)
  523.         {        cerr<<"\nnot a squre matrix, can't use Cholesky disintegration";
  524.                 return FALSE;
  525.         }
  526.         if((f[0][0]+1.0==1.0)||(f[0][0]<0.0))
  527.         {        cerr<<"\nnot a Zhengdin matrix, can't use Cholesky disintegration";
  528.                 return FALSE;
  529.         }
  530.         f[0][0]=sqrt(f[0][0]);
  531.         d=f[0][0];
  532.         for(i=1;i<=row-1;i++)
  533.         {        f[i][0]/=f[0][0];
  534.         }
  535.         for(j=1;j<=row-1;j++)
  536.         {        for(k=0;k<=j-1;k++)
  537.                 {   f[j][j]-=f[j][k]*f[j][k];
  538.                 }
  539.         if((f[j][j]+1.0==1.0)||(f[j][j]<0.0))
  540.                 {   cerr<<"\nnot a zhendin matrix, can't use Cholesky disintegration";
  541.                     return FALSE;
  542.                 }
  543.                 f[j][j]=sqrt(f[j][j]);
  544.                 d*=f[j][j];
  545.             for(i=j+1;i<=row-1;i++)
  546.                 {        for(k=0;k<=j-1;k++)
  547.                 f[i][j]-=f[i][k]*f[j][k];
  548.                     f[i][j]/=f[j][j];
  549.                 }
  550.         }
  551.         for(i=0;i<=row-2;i++)
  552.                 for(j=i+1;j<=row-1;j++)
  553.                         f[i][j]=0.0;
  554.     return TRUE;
  555. }
  556. template<class Type>       
  557. CMatrix<Type> CMatrix<Type>::Jacobi(double eps,int jt)
  558. {
  559.                 CMatrix<Type> v;
  560.                 v.Zeros(row,col);
  561.                 if(row!=col) return v;
  562.                 int i,j,p,q,l,n;
  563.                 n=row;
  564.                 for(i=0;i<=n-1;i++)    // check the matrix's symmetrition
  565.                         for(j=0;j<=n-1;j++)
  566.                                 if((f[i][j]-f[j][i])>0.001)
  567.                                         return v;
  568.                 double fm,cn,sn,omega,x,y,d;
  569.                 l=1;
  570.                 for (i=0; i<=n-1; i++)
  571.                 {
  572.                         v[i][i]=1.0;
  573.                         for (j=0; j<=n-1; j++)
  574.                         if (i!=j) v[i][j]=0.0;
  575.                 }
  576.     while (1==1)//????????????????????????????????????
  577.       { fm=0.0;
  578.         for (i=0; i<=n-1; i++)
  579.         for (j=0; j<=n-1; j++)
  580.           { d=fabs(f[i][j]);
  581.             if ((i!=j)&&(d>fm))
  582.               { fm=d; p=i; q=j;}
  583.           }
  584.         if (fm<eps)  return v;
  585.         if (l>jt)  return v;
  586.         l=l+1;
  587.         x=-f[p][q]; y=(f[q][q]-f[p][p])/2.0;
  588.         omega=x/sqrt(x*x+y*y);
  589.         if (y<0.0) omega=-omega;
  590.         sn=1.0+sqrt(1.0-omega*omega);
  591.         sn=omega/sqrt(2.0*sn);
  592.         cn=sqrt(1.0-sn*sn);
  593.         fm=f[p][p];
  594.         f[p][p]=fm*cn*cn+f[q][q]*sn*sn+f[p][q]*omega;
  595.         f[q][q]=fm*sn*sn+f[q][q]*cn*cn-f[p][q]*omega;
  596.         f[p][q]=0.0; f[q][p]=0.0;
  597.         for (j=0; j<=n-1; j++)
  598.         if ((j!=p)&&(j!=q))
  599.         {
  600.             fm=f[p][j];
  601.             f[p][j]=fm*cn+f[q][j]*sn;
  602.             f[q][j]=-fm*sn+f[q][j]*cn;
  603.           }
  604.         for (i=0; i<=n-1; i++)
  605.           if ((i!=p)&&(i!=q))
  606.           {
  607.               fm=f[i][p];
  608.               f[i][p]=fm*cn+f[i][q]*sn;
  609.               f[i][q]=-fm*sn+f[i][q]*cn;
  610.             }
  611.         for (i=0; i<=n-1; i++)
  612.           {
  613.             fm=v[i][p];
  614.             v[i][p]=fm*cn+v[i][q]*sn;
  615.             v[i][q]=-fm*sn+v[i][q]*cn;
  616.           }
  617.       }
  618.     return v;
  619. }




  620. template<class Type>
  621. CMatrix<double> CMatrix<Type>::QREigen(double eps,int jt)
  622. {              // return eigenvalue in two row matrix of a real matrix
  623.         int m,it,i,j,k,l,ii,jj,kk,ll;
  624.     CMatrix<double> uv;
  625.         uv.Zeros(row,2);
  626.         if(row!=col) return uv;
  627.         int n=row;
  628.     double b,c,w,g,xy,p,q,r,x,s,e,ff,z,y;
  629.     double *u,*v,*a;
  630.     u=(double*)calloc(n,sizeof(double));
  631.     v=(double*)calloc(n,sizeof(double));
  632.     a=(double*)calloc(n*n,sizeof(double));
  633.     this->Hessenberg();
  634.         for(i=0;i<n;i++)
  635.                 for(j=0;j<n;j++)
  636.                         a[i*n+j]=f[i][j];
  637.         it=0; m=n;
  638.     while (m!=0)
  639.       { l=m-1;
  640.         while ((l>0)&&(fabs(a[l*n+l-1])>eps*
  641.               (fabs(a[(l-1)*n+l-1])+fabs(a[l*n+l])))) l=l-1;
  642.         ii=(m-1)*n+m-1; jj=(m-1)*n+m-2;
  643.         kk=(m-2)*n+m-1; ll=(m-2)*n+m-2;
  644.         if (l==m-1)
  645.           { u[m-1]=a[(m-1)*n+m-1]; v[m-1]=0.0;
  646.             m=m-1; it=0;
  647.           }
  648.         else if (l==m-2)
  649.           { b=-(a[ii]+a[ll]);
  650.             c=a[ii]*a[ll]-a[jj]*a[kk];
  651.             w=b*b-4.0*c;
  652.             y=sqrt(fabs(w));
  653.             if (w>0.0)
  654.               { xy=1.0;
  655.                 if (b<0.0) xy=-1.0;
  656.                 u[m-1]=(-b-xy*y)/2.0;
  657.                 u[m-2]=c/u[m-1];
  658.                 v[m-1]=0.0; v[m-2]=0.0;
  659.               }
  660.             else
  661.               { u[m-1]=-b/2.0; u[m-2]=u[m-1];
  662.                 v[m-1]=y/2.0; v[m-2]=-v[m-1];
  663.               }
  664.             m=m-2; it=0;
  665.           }
  666.         else
  667.           { if (it>=jt)
  668.               { cout<<"fail\n";
  669.                 return uv;
  670.               }
  671.             it=it+1;
  672.             for (j=l+2; j<=m-1; j++)
  673.               a[j*n+j-2]=0.0;
  674.             for (j=l+3; j<=m-1; j++)
  675.               a[j*n+j-3]=0.0;
  676.             for (k=l; k<=m-2; k++)
  677.               { if (k!=l)
  678.                   { p=a[k*n+k-1]; q=a[(k+1)*n+k-1];
  679.                     r=0.0;
  680.                     if (k!=m-2) r=a[(k+2)*n+k-1];
  681.                   }
  682.                 else
  683.                   { x=a[ii]+a[ll];
  684.                     y=a[ll]*a[ii]-a[kk]*a[jj];
  685.                     ii=l*n+l; jj=l*n+l+1;
  686.                     kk=(l+1)*n+l; ll=(l+1)*n+l+1;
  687.                     p=a[ii]*(a[ii]-x)+a[jj]*a[kk]+y;
  688.                     q=a[kk]*(a[ii]+a[ll]-x);
  689.                     r=a[kk]*a[(l+2)*n+l+1];
  690.                   }
  691.                 if ((fabs(p)+fabs(q)+fabs(r))!=0.0)
  692.                   { xy=1.0;
  693.                     if (p<0.0) xy=-1.0;
  694.                     s=xy*sqrt(p*p+q*q+r*r);
  695.                     if (k!=l) a[k*n+k-1]=-s;
  696.                     e=-q/s; ff=-r/s; x=-p/s;
  697.                     y=-x-ff*r/(p+s);
  698.                     g=e*r/(p+s);
  699.                     z=-x-e*q/(p+s);
  700.                     for (j=k; j<=m-1; j++)
  701.                       { ii=k*n+j; jj=(k+1)*n+j;
  702.                         p=x*a[ii]+e*a[jj];
  703.                         q=e*a[ii]+y*a[jj];
  704.                         r=ff*a[ii]+g*a[jj];
  705.                         if (k!=m-2)
  706.                           { kk=(k+2)*n+j;
  707.                             p=p+ff*a[kk];
  708.                             q=q+g*a[kk];
  709.                             r=r+z*a[kk]; a[kk]=r;
  710.                           }
  711.                         a[jj]=q; a[ii]=p;
  712.                       }
  713.                     j=k+3;
  714.                     if (j>=m-1) j=m-1;
  715.                     for (i=l; i<=j; i++)
  716.                       { ii=i*n+k; jj=i*n+k+1;
  717.                         p=x*a[ii]+e*a[jj];
  718.                         q=e*a[ii]+y*a[jj];
  719.                         r=ff*a[ii]+g*a[jj];
  720.                         if (k!=m-2)
  721.                           { kk=i*n+k+2;
  722.                             p=p+ff*a[kk];
  723.                             q=q+g*a[kk];
  724.                             r=r+z*a[kk]; a[kk]=r;
  725.                           }
  726.                         a[jj]=q; a[ii]=p;
  727.                       }
  728.                   }
  729.               }
  730.           }
  731.       }

  732.     for(i=0;i<n;i++)
  733.                 uv[i][0]=u[i];
  734.         for(i=0;i<n;i++)
  735.                 uv[i][1]=v[i];
  736.         return uv;
  737.   }
复制代码
 楼主| 发表于 2006-10-10 00:42 | 显示全部楼层
text.cpp如下:
  1. #include "matrix.h"
  2. #include <math.h>
  3. #include <fstream.h>
  4. #include <malloc.h>

  5. const unsigned char Z_RADIANS = 0;
  6. const unsigned char Z_DEGREES = 1;
  7. const unsigned char Z_COMMA   = 0;        // (x, y)
  8. const unsigned char Z_LETTER  = 1;        // x + iy
  9. const double M_PI  = 1.1415926;       
  10. class complex
  11. {
  12. public:
  13.   double re, im;

  14. private:
  15.   static unsigned char zArgMode;
  16.   static unsigned char zPrintMode;
  17.   static unsigned char zLetter;

  18. public:
  19.   complex(void): re(0), im(0) {}
  20.   complex(const double real, const double imag=0): re(real), im(imag) {}
  21.   complex(const complex& z): re(z.re), im(z.im) {}

  22.   friend double    re(const complex& z) {        // real part
  23.     return z.re;
  24.   }
  25.   friend double    im(const complex& z) {        // imaginary part
  26.     return z.im;
  27.   }
  28.   friend double  real(const complex& z) {        // real part
  29.     return z.re;
  30.   }
  31.   friend double  imag(const complex& z) {        // imaginary part
  32.     return z.im;
  33.   }
  34.   friend double   mag(const complex& z) {        // magnitude |z|
  35.     return sqrt(z.re*z.re + z.im*z.im);
  36.   }
  37.   friend double   arg(const complex& z);        // argument
  38.   friend double   ang(const complex& z) {        // angle
  39.     return arg(z);
  40.   }
  41.   friend double    ph(const complex& z) {        // phase
  42.     return arg(z);
  43.   }
  44.   friend complex conj(const complex& z) {        // complex conjugate
  45.     return complex(z.re, -z.im);
  46.   }
  47.   friend double  norm(const complex& z) {        // norm
  48.     return z.re*z.re + z.im*z.im;
  49.   }

  50.   friend complex rtop(double x,   double y=0);
  51.   friend complex ptor(double mag, double angle=0);
  52.   complex& topolar(void);
  53.   complex& torect(void);

  54.   void operator = (const complex& z) {                // z1 = z2
  55.     re = z.re;
  56.     im = z.im;
  57.   }
  58.   complex& operator += (const complex& z) {        // z1 += z2
  59.     re += z.re;
  60.     im += z.im;
  61.     return *this;
  62.   }
  63.   complex& operator -= (const complex& z) {        // z1 -= z2
  64.     re -= z.re;
  65.     im -= z.im;
  66.     return *this;
  67.   }
  68.   complex& operator *= (const complex& z) {        // z1 *= z2
  69.     *this = *this * z;
  70.     return *this;
  71.   }
  72.   complex& operator /= (const complex& z) {        // z1 /= z2
  73.     *this = *this / z;
  74.     return *this;
  75.   }
  76.   complex operator + (void) const {                // +z1
  77.     return *this;
  78.   }
  79.   complex operator - (void) const {                // -z1
  80.     return complex(-re, -im);
  81.   }

  82.   friend complex operator + (const complex& z1, const complex& z2) {
  83.     return complex(z1.re + z2.re, z1.im + z2.im);
  84.   }
  85.   friend complex operator + (const complex& z, const double x) {
  86.     return complex(z.re+x, z.im);
  87.   }
  88.   friend complex operator + (const double x, const complex& z) {
  89.     return complex(z.re+x, z.im);
  90.   }
  91.   friend complex operator - (const complex& z1, const complex& z2) {
  92.     return complex(z1.re - z2.re, z1.im - z2.im);
  93.   }
  94.   friend complex operator - (const complex&, const double);
  95.   friend complex operator - (const double x, const complex& z) {
  96.     return complex(x-z.re, -z.im);
  97.   }
  98.   friend complex operator * (const complex& z1, const complex& z2) {
  99.     double re = z1.re*z2.re - z1.im*z2.im;
  100.     double im = z1.re*z2.im + z1.im*z2.re;
  101.     return complex(re, im);
  102.   }
  103.   friend complex operator * (const complex& z, const double x) {
  104.     return complex(z.re*x, z.im*x);
  105.   }
  106.   friend complex operator * (const double x, const complex& z) {
  107.     return complex(z.re*x, z.im*x);
  108.   }
  109.   friend complex operator / (const complex&, const complex&);
  110.   friend complex operator / (const complex& z, const double x) {
  111.     return complex(z.re/x, z.im/x);
  112.   }
  113.   friend complex operator / (const double, const complex&);
  114.   friend complex operator ^ (const complex& z1, const complex& z2) {
  115.     return pow(z1, z2);
  116.   }

  117.   friend int operator == (const complex& z1, const complex& z2) {
  118.     return (z1.re == z2.re) && (z1.im == z2.im);
  119.   }
  120.   friend int operator != (const complex& z1, const complex& z2) {
  121.     return (z1.re != z2.re) || (z1.im != z2.im);
  122.   }

  123.   friend double   abs(const complex& z);
  124.   friend complex sqrt(const complex& z);
  125.   friend complex pow(const complex& base, const complex& exp);
  126.   friend complex pow(const complex& base, const double   exp);
  127.   friend complex pow(const double   base, const complex& exp);

  128.   friend complex   exp(const complex& z);
  129.   friend complex   log(const complex& z);
  130.   friend complex    ln(const complex& z);
  131.   friend complex log10(const complex& z);

  132.   friend complex  cos(const complex& z);
  133.   friend complex  sin(const complex& z);
  134.   friend complex  tan(const complex& z);

  135.   friend complex asin(const complex& z);
  136.   friend complex acos(const complex& z);
  137.   friend complex atan(const complex& z);

  138.   friend complex sinh(const complex& z);
  139.   friend complex cosh(const complex& z);
  140.   friend complex tanh(const complex& z);

  141.   void SetArgMode(unsigned char mode) const {
  142.     if(mode == Z_RADIANS || mode == Z_DEGREES)
  143.       zArgMode = mode;
  144.   }
  145.   void SetPrintMode(unsigned char mode) const {
  146.     if(mode == Z_COMMA || mode == Z_LETTER)
  147.       zPrintMode = mode;
  148.   }
  149.   void SetLetter(unsigned char letter) const {
  150.     zLetter = letter;
  151.   }

  152.   friend ostream& operator<<(ostream&, const complex&);
  153.   friend istream& operator>>(istream&, const complex&);
  154. };

  155. static const complex Z0(0, 0);                // complex number 0
  156. static const complex Z1(1, 0);                // complex number 1
  157. static const complex Zi(0, 1);                // complex number i
  158. static const complex Zinf(HUGE_VAL, HUGE_VAL); // complex number infinity
  159. static const complex Complex;
  160. ///////////////////////////////////////////////
  161. /////////////////////////////////////////////////
  162. ///////////////////////////////////////////////
  163. unsigned char complex::zArgMode   = Z_RADIANS;
  164. unsigned char complex::zPrintMode = Z_COMMA;
  165. unsigned char complex::zLetter    = 'i';

  166. /* -------------------------------------------------------------------- */

  167. double arg(const complex& z)                // argument (angle)
  168. {
  169.   if(z.re == 0 && z.im == 0)                // this is actually a domain error
  170.     return 0;
  171.   if(complex::zArgMode == Z_RADIANS)
  172.     return atan2(z.im, z.re);
  173.   return atan2(z.im, z.re)/M_PI*180;
  174. }

  175. complex ptor(double mag, double angle)  // polar-to-rectangular
  176. {
  177.   if(complex::zArgMode == Z_RADIANS)
  178.     return complex(mag*cos(angle), mag*sin(angle));
  179.   return complex(mag*cos(angle/180*M_PI), mag*sin(angle/180*M_PI));
  180. }

  181. complex rtop(double x, double y)        // rectangular-to-polar
  182. {
  183.   if(x == 0 && y == 0)                        // this is actually a domain error
  184.     return Z0;
  185.   if(complex::zArgMode == Z_RADIANS)
  186.     return complex(sqrt(x*x + y*y), atan2(y, x));
  187.   return complex(sqrt(x*x + y*y), atan2(y, x)*180/M_PI);
  188. }

  189. complex& complex::topolar(void)
  190. {
  191.   double re_tmp = re;

  192.   if(re != 0 || im != 0)                // z = (0,0) is a domain error
  193.   {
  194.     re = sqrt(re*re + im*im);
  195.     im = atan2(im, re_tmp);
  196.   }

  197.   if(complex::zArgMode == Z_DEGREES)
  198.     im *= (180/M_PI);

  199.   return *this;
  200. }

  201. complex& complex::torect(void)
  202. {
  203.   double re_tmp = re;

  204.   re = re_tmp*cos(im);
  205.   im = re_tmp*sin(im);

  206.   return *this;
  207. }

  208. /* ----- Operators ---------------------------------------------------- */

  209. complex operator/(const complex& z1, const complex& z2)
  210. {
  211.   if(z2 == Z0)
  212.     return complex(Zinf);                // z2 = Z0 is an error!

  213.   double denom = z2.re*z2.re + z2.im*z2.im;
  214.   double re = (z1.re*z2.re + z1.im*z2.im)/denom;
  215.   double im = (z2.re*z1.im - z2.im*z1.re)/denom;
  216.   return complex(re, im);
  217. }

  218. complex operator/(const double x, const complex& z)
  219. {
  220.   if(z == Z0)
  221.     return complex(Zinf);                // z = Z0 is an error!

  222.   double denom = z.re*z.re + z.im*z.im;
  223.   return complex(x*z.re/denom, -z.im*x/denom);
  224. }

  225. /* ----- Math functions ----------------------------------------------- */

  226. double abs(const complex& z)
  227. {
  228.   return sqrt(z.re*z.re + z.im*z.im);
  229. }

  230. complex sqrt(const complex& z)
  231. {
  232.   return ptor(sqrt(abs(z)), arg(z)/2);
  233. }

  234. complex pow(const complex& base, const double exponent)
  235. {
  236.   if(base != Z0 && exponent == 0.0)
  237.     return complex(1,0);

  238.   if (base == Z0 && exponent > 0)
  239.     return Z0;

  240.   // base == Z0 && exponent == 0 is undefined!

  241.   return ptor(pow(abs(base), exponent), exponent*arg(base));
  242. }

  243. complex pow(const double base, const complex& exponent)
  244. {
  245.   if(base != 0.0 && exponent == Z0)
  246.     return complex(1,0);

  247.   if (base == 0 && re(exponent) > 0)
  248.     return complex(0,0);

  249.   // base == 0 && re(exponent) == 0 is undefined!

  250.   if(base > 0.0)
  251.     return exp(exponent * log(fabs(base)));

  252.   return exp(exponent * complex(log(fabs(base)), M_PI));
  253. }

  254. complex pow(const complex& base, const complex& exponent)
  255. {
  256.   if(base != Z0 && exponent == Z0)
  257.     return complex(1,0);

  258.   if(base == Z0 && re(exponent) > 0)
  259.     return complex(0,0);

  260.   // base == Z0 && re(exponent) == 0 is undefined!

  261.   return exp(exponent * log(base));
  262. }

  263. /* ----- Trig functions ----------------------------------------------- */

  264. complex exp(const complex& z)
  265. {
  266.   double mag = exp(z.re);
  267.   return complex(mag*cos(z.im), mag*sin(z.im));
  268. }

  269. complex log(const complex& z)
  270. {
  271.   return complex(log(mag(z)), atan2(z.im, z.re));
  272. }
  273. /*
  274. complex log10(const complex& z)
  275. {
  276.   return log(z) * M_LOG10E;
  277. }
  278. */
  279. complex sin(const complex& z)
  280. {
  281.   return (exp(Zi*z) - exp(-Zi*z))/(2*Zi);
  282. }

  283. complex cos(const complex& z)
  284. {
  285.   return (exp(Zi*z) + exp(-Zi*z))/2;
  286. }

  287. complex tan(const complex& z)
  288. {
  289.   return sin(z)/cos(z);
  290. }

  291. complex asin(const complex& z)
  292. {
  293.   return -Zi*log(Zi*z+sqrt(1-z*z));
  294. }

  295. complex acos(const complex& z)
  296. {
  297.   return -Zi*log(z+Zi*sqrt(1-z*z));
  298. }

  299. complex atan(const complex& z)
  300. {
  301.   return -0.5*Zi * log((1+Zi*z)/(1-Zi*z));
  302. }

  303. complex sinh(const complex& z)
  304. {
  305.   return (exp(z) - exp(-z))/2;
  306. }

  307. complex cosh(const complex& z)
  308. {
  309.   return (exp(z) + exp(-z))/2;
  310. }

  311. complex tanh(const complex& z)
  312. {
  313.   return sinh(z)/cosh(z);
  314. }

  315. /* ----- Stream I/O --------------------------------------------------- */

  316. ostream& operator<<(ostream& s, const complex& z)
  317. {
  318.   char sign[] = "   ";

  319.   if(complex::zPrintMode == Z_COMMA)
  320.     return s << "(" << z.re << ", " << z.im << ")";

  321.   if(z.im == 0 || z.im/fabs(z.im) == 1)
  322.     sign[1] = '+';
  323.   else
  324.     sign[1] = '-';
  325.   return s << z.re << sign << complex::zLetter << fabs(z.im);

  326. }

  327. istream& operator>>(istream& s, const complex& z)
  328. {
  329.   char ch;

  330.   s >> ch;
  331.   if(ch == '(')
  332.   {
  333.     s >> z.re >> ch;
  334.     if(ch == ',')
  335.       s >> z.im >> ch;
  336.     if(ch != ')')
  337.       s.clear(ios::badbit | s.rdstate());
  338.   }
  339.   else
  340.   {
  341.     s.putback(ch);
  342.     s >> z.re;
  343.   }

  344.   return s;
  345. }
  346. ///////////////////////////////////////
  347. ////////////////////fft
  348. void Fft(complex CA[],int n,int k,complex CB[],int l,int il)
  349. {
  350.     int it,m,is,i,j,nv,l0;
  351.     double p,q,s,vr,vi,poddr,poddi;
  352.         double *pr,*pi,*fr,*fi;
  353.         pr=(double*)malloc(n*sizeof(double));
  354.     pi=(double*)malloc(n*sizeof(double));
  355.         fr=(double*)malloc(n*sizeof(double));
  356.         fi=(double*)malloc(n*sizeof(double));
  357.         for(i=0;i<n;i++)
  358.         {
  359.                 pr[i]=CA[i].re;
  360.                 pi[i]=CA[i].im;
  361.         }
  362.     for (it=0; it<=n-1; it++)
  363.       { m=it; is=0;
  364.         for (i=0; i<=k-1; i++)
  365.           { j=m/2; is=2*is+(m-2*j); m=j;}
  366.         fr[it]=pr[is]; fi[it]=pi[is];
  367.       }
  368.     pr[0]=1.0; pi[0]=0.0;
  369.     p=6.283185306/(1.0*n);
  370.     pr[1]=cos(p); pi[1]=-sin(p);
  371.     if (l!=0) pi[1]=-pi[1];
  372.     for (i=2; i<=n-1; i++)
  373.       { p=pr[i-1]*pr[1]; q=pi[i-1]*pi[1];
  374.         s=(pr[i-1]+pi[i-1])*(pr[1]+pi[1]);
  375.         pr[i]=p-q; pi[i]=s-p-q;
  376.       }
  377.     for (it=0; it<=n-2; it=it+2)
  378.       { vr=fr[it]; vi=fi[it];
  379.         fr[it]=vr+fr[it+1]; fi[it]=vi+fi[it+1];
  380.         fr[it+1]=vr-fr[it+1]; fi[it+1]=vi-fi[it+1];
  381.       }
  382.     m=n/2; nv=2;
  383.     for (l0=k-2; l0>=0; l0--)
  384.       { m=m/2; nv=2*nv;
  385.         for (it=0; it<=(m-1)*nv; it=it+nv)
  386.           for (j=0; j<=(nv/2)-1; j++)
  387.             { p=pr[m*j]*fr[it+j+nv/2];
  388.               q=pi[m*j]*fi[it+j+nv/2];
  389.               s=pr[m*j]+pi[m*j];
  390.               s=s*(fr[it+j+nv/2]+fi[it+j+nv/2]);
  391.               poddr=p-q; poddi=s-p-q;
  392.               fr[it+j+nv/2]=fr[it+j]-poddr;
  393.               fi[it+j+nv/2]=fi[it+j]-poddi;
  394.               fr[it+j]=fr[it+j]+poddr;
  395.               fi[it+j]=fi[it+j]+poddi;
  396.             }
  397.       }
  398.     if (l!=0)
  399.       for (i=0; i<=n-1; i++)
  400.         { fr[i]=fr[i]/(1.0*n);
  401.           fi[i]=fi[i]/(1.0*n);
  402.         }
  403.     if (il!=0)
  404.       for (i=0; i<=n-1; i++)
  405.         { pr[i]=sqrt(fr[i]*fr[i]+fi[i]*fi[i]);
  406.           if (fabs(fr[i])<0.000001*fabs(fi[i]))
  407.             { if ((fi[i]*fr[i])>0) pi[i]=90.0;
  408.               else pi[i]=-90.0;
  409.             }
  410.           else
  411.             pi[i]=atan(fi[i]/fr[i])*360.0/6.283185306;
  412.         }
  413.         for(i=0;i<n;i++)
  414.         {
  415.                 CA[i].re=pr[i];
  416.                 CA[i].im=pi[i];
  417.         }
  418.    
  419.           for(i=0;i<n;i++)
  420.           {
  421.                   CB[i].re=fr[i];
  422.                   CB[i].im=fi[i];
  423.           }
  424.     return;
  425.   }
  426. /////////////////////////////////////
  427. void  main()
  428. {
  429.     complex a,b;
  430.         a.re=2;
  431.         a.im=3;
  432.         b=a;
  433.         b=exp(a);
  434.         cout<<b;
  435.         int n=64,i,j;
  436.         double deltaT=0.1,R;
  437.         ifstream ifile("d:\\work\\tj.fft");
  438.         ofstream ofile("d:\\work\\tj.out");
  439.         /*for(i=0;i<n;i++)
  440.        ofile<<exp(-i*deltaT)<<endl;
  441.        
  442.         complex q;
  443.         double L;
  444.         int j;
  445.         for(L=0;L<n;L++)
  446.         {
  447.                 ifile.seekg(ios::beg);
  448.                 q=0;
  449.                 for(j=0;j<n;j++)
  450.                 {
  451.                         ifile>>R;
  452.                         q+=R*exp(-2*M_PI*L*Zi*L*j/n);
  453.                 }
  454.                 q*=deltaT;
  455.                 ofile<<q<<endl;
  456.         }
  457.         CMatrix<int> A;
  458.         A.Ones(3);
  459.         cout<<A;
  460.     CMatrix<complex> B;
  461.         B.Ones(3);
  462.         cout<<B;
  463. */
  464.         complex CA[64];
  465.         complex p[64],f[64];
  466.     for(i=0;i<64;i++)
  467.         {
  468.                 ifile>>p[i];
  469.         }
  470.         Fft(p,64,6,f,1,1);
  471.         for(i=0;i<=15;i++)
  472.         {
  473.                 for(j=0;j<=3;j++)
  474.                         ofile<<f[4*i+j]<<"    ";
  475.                 ofile<<endl;
  476.         }
  477.         ofile<<endl<<endl<<endl;

  478. for(i=0;i<=15;i++)
  479.         {
  480.                 for(j=0;j<=3;j++)
  481.                         ofile<<p[4*i+j]<<"    ";
  482.                 ofile<<endl;
  483.         }



  484.         return ;
  485. };
复制代码
发表于 2007-9-20 19:36 | 显示全部楼层
:lol
发表于 2007-9-21 09:39 | 显示全部楼层
有人测试过了吗?
 楼主| 发表于 2007-10-11 09:23 | 显示全部楼层
您需要登录后才可以回帖 登录 | 我要加入

本版积分规则

QQ|小黑屋|Archiver|手机版|联系我们|声振论坛

GMT+8, 2024-5-12 05:30 , Processed in 0.238831 second(s), 18 queries , Gzip On.

Powered by Discuz! X3.4

Copyright © 2001-2021, Tencent Cloud.

快速回复 返回顶部 返回列表