⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 ch3.h

📁 将C语言的常用程序集移植到VC开发环境的源代码
💻 H
字号:
/************************************************
 Expect bugs!
 Please use and enjoy, and let me know of any bugs/mods/improvements 
 that you have found/implemented and I will fix/incorporate them into 
 this file. Thank Mr. Xushiliang once again.

					hujinshan@2002.11.3
				Airforce Engineering University
************************************************/

/*****  #include "CH3.h" 矩阵特征值与特征向量的计算  *****/
#ifndef CH3_H_
#define CH3_H_

#include "stdlib.h"
#include "math.h"
#include "stdio.h"
//*******************************************************************

void cstrq(double a[],int n,double q[],double b[],double c[]);//约化对称矩阵为对称三对角的豪斯荷尔德变换法
int csstq(int n,double b[],double c[],double q[],double eps,int l);//实对称三对角陈的全部特征值与特征向量的计算
void chhbg(double a[],int n);//约化一般实矩阵为赫申伯格矩阵的初等相似变换法
int chhqr(double a[],int n,double u[],double v[],double eps,int jt);;//求赫申伯格矩阵全部特征值的QR方法
int cjcbi(double a[],int n,double v[],double eps,int jt);//求实对称矩阵特征值与特征向量的雅可比法
void cjcbj(double a[],int n,double v[],double eps);//求实对称矩阵特征值与特征向量的雅可比过关法

//*******************************************************************
int chhqr(double a[],int n,double u[],double v[],double eps,int jt)
{ 
	int m,it,i,j,k,l,ii,jj,kk,ll;
  double b,c,w,g,xy,p,q,r,x,s,e,f,z,y;
  it=0; m=n;
  while (m!=0)
    { l=m-1;
      while ((l>0)&&(fabs(a[l*n+l-1])>eps*
	      (fabs(a[(l-1)*n+l-1])+fabs(a[l*n+l])))) l=l-1;
      ii=(m-1)*n+m-1; jj=(m-1)*n+m-2;
      kk=(m-2)*n+m-1; ll=(m-2)*n+m-2;
      if (l==m-1)
        { u[m-1]=a[(m-1)*n+m-1]; v[m-1]=0.0;
          m=m-1; it=0;
        }
      else if (l==m-2)
        { b=-(a[ii]+a[ll]);
          c=a[ii]*a[ll]-a[jj]*a[kk];
          w=b*b-4.0*c;
          y=sqrt(fabs(w));
          if (w>0.0)
            { xy=1.0;
              if (b<0.0) xy=-1.0;
              u[m-1]=(-b-xy*y)/2.0;
              u[m-2]=c/u[m-1];
              v[m-1]=0.0; v[m-2]=0.0;
            }
          else
            { u[m-1]=-b/2.0; u[m-2]=u[m-1];
              v[m-1]=y/2.0; v[m-2]=-v[m-1];
            }
          m=m-2; it=0;
        }
      else
        { if (it>=jt)
            { printf("fail\n");
              return(-1);
            }
          it=it+1;
          for (j=l+2; j<=m-1; j++)
            a[j*n+j-2]=0.0;
          for (j=l+3; j<=m-1; j++)
            a[j*n+j-3]=0.0;
          for (k=l; k<=m-2; k++)
            { if (k!=l)
                { p=a[k*n+k-1]; q=a[(k+1)*n+k-1];
                  r=0.0;
                  if (k!=m-2) r=a[(k+2)*n+k-1];
                }
              else
                { x=a[ii]+a[ll];
                  y=a[ll]*a[ii]-a[kk]*a[jj];
                  ii=l*n+l; jj=l*n+l+1;
                  kk=(l+1)*n+l; ll=(l+1)*n+l+1;
                  p=a[ii]*(a[ii]-x)+a[jj]*a[kk]+y;
                  q=a[kk]*(a[ii]+a[ll]-x);
                  r=a[kk]*a[(l+2)*n+l+1];
                }
              if ((fabs(p)+fabs(q)+fabs(r))!=0.0)
                { xy=1.0;
                  if (p<0.0) xy=-1.0;
                  s=xy*sqrt(p*p+q*q+r*r);
                  if (k!=l) a[k*n+k-1]=-s;
                  e=-q/s; f=-r/s; x=-p/s;
                  y=-x-f*r/(p+s);
                  g=e*r/(p+s);
                  z=-x-e*q/(p+s);
                  for (j=k; j<=m-1; j++)
                    { ii=k*n+j; jj=(k+1)*n+j;
                      p=x*a[ii]+e*a[jj];
                      q=e*a[ii]+y*a[jj];
                      r=f*a[ii]+g*a[jj];
                      if (k!=m-2)
                        { kk=(k+2)*n+j;
                          p=p+f*a[kk];
                          q=q+g*a[kk];
                          r=r+z*a[kk]; a[kk]=r;
                        }
                      a[jj]=q; a[ii]=p;
                    }
                  j=k+3;
                  if (j>=m-1) j=m-1;
                  for (i=l; i<=j; i++)
                    { ii=i*n+k; jj=i*n+k+1;
                      p=x*a[ii]+e*a[jj];
                      q=e*a[ii]+y*a[jj];
                      r=f*a[ii]+g*a[jj];
                      if (k!=m-2)
                        { kk=i*n+k+2;
                          p=p+f*a[kk];
                          q=q+g*a[kk];
                          r=r+z*a[kk]; a[kk]=r;
                        }
                      a[jj]=q; a[ii]=p;
                    }
                }
            }
        }
    }
  return(1);
}
/////////////////////////////////////////////////////////////
void cstrq(double a[],int n,double q[],double b[],double c[])
{ int i,j,k,u;//,v
  double h,f,g,h2;
  for (i=0; i<=n-1; i++)
  for (j=0; j<=n-1; j++)
    { u=i*n+j; q[u]=a[u];}
  for (i=n-1; i>=1; i--)
    { h=0.0;
      if (i>1)
        for (k=0; k<=i-1; k++)
          { u=i*n+k; h=h+q[u]*q[u];}
      if (h+1.0==1.0)
        { c[i]=0.0;
          if (i==1) c[i]=q[i*n+i-1];
          b[i]=0.0;
        }
      else
        { c[i]=sqrt(h);
          u=i*n+i-1;
          if (q[u]>0.0) c[i]=-c[i];
          h=h-q[u]*c[i];
          q[u]=q[u]-c[i];
          f=0.0;
          for (j=0; j<=i-1; j++)
            { q[j*n+i]=q[i*n+j]/h;
              g=0.0;
              for (k=0; k<=j; k++)
                g=g+q[j*n+k]*q[i*n+k];
              if (j+1<=i-1)
                for (k=j+1; k<=i-1; k++)
                  g=g+q[k*n+j]*q[i*n+k];
              c[j]=g/h;
              f=f+g*q[j*n+i];
            }
          h2=f/(h+h);
          for (j=0; j<=i-1; j++)
            { f=q[i*n+j];
              g=c[j]-h2*f;
              c[j]=g;
              for (k=0; k<=j; k++)
                { u=j*n+k;
                  q[u]=q[u]-f*c[k]-g*q[i*n+k];
                }
            }
          b[i]=h;
        }
    }
  for (i=0; i<=n-2; i++) c[i]=c[i+1];
  c[n-1]=0.0;
  b[0]=0.0;
  for (i=0; i<=n-1; i++)
    { if ((b[i]!=0.0)&&(i-1>=0))
        for (j=0; j<=i-1; j++)
          { g=0.0;
            for (k=0; k<=i-1; k++)
              g=g+q[i*n+k]*q[k*n+j];
            for (k=0; k<=i-1; k++)
              { u=k*n+j;
                q[u]=q[u]-g*q[k*n+i];
              }
          }
      u=i*n+i;
      b[i]=q[u]; q[u]=1.0;
      if (i-1>=0)
        for (j=0; j<=i-1; j++)
          { q[i*n+j]=0.0; q[j*n+i]=0.0;}
    }
  return;
}
/////////////////////////////////////////////////////////////
int csstq(int n,double b[],double c[],double q[],double eps,int l)
{ int i,j,k,m,it,u,v;
  double d,f,h,g,p,r,e,s;
  c[n-1]=0.0; d=0.0; f=0.0;
  for (j=0; j<=n-1; j++)
    { it=0;
      h=eps*(fabs(b[j])+fabs(c[j]));
      if (h>d) d=h;
      m=j;
      while ((m<=n-1)&&(fabs(c[m])>d)) m=m+1;
      if (m!=j)
        { do
            { if (it==l)
                { printf("fail\n");
                  return(-1);
                }
              it=it+1;
              g=b[j];
              p=(b[j+1]-g)/(2.0*c[j]);
              r=sqrt(p*p+1.0);
              if (p>=0.0) b[j]=c[j]/(p+r);
              else b[j]=c[j]/(p-r);
              h=g-b[j];
              for (i=j+1; i<=n-1; i++)
                b[i]=b[i]-h;
              f=f+h; p=b[m]; e=1.0; s=0.0;
              for (i=m-1; i>=j; i--)
                { g=e*c[i]; h=e*p;
                  if (fabs(p)>=fabs(c[i]))
                    { e=c[i]/p; r=sqrt(e*e+1.0);
                      c[i+1]=s*p*r; s=e/r; e=1.0/r;
                    }
                  else
		      { e=p/c[i]; r=sqrt(e*e+1.0);
                      c[i+1]=s*c[i]*r;
                      s=1.0/r; e=e/r;
                    }
                  p=e*b[i]-s*g;
                  b[i+1]=h+s*(e*g+s*b[i]);
                  for (k=0; k<=n-1; k++)
                    { u=k*n+i+1; v=u-1;
                      h=q[u]; q[u]=s*q[v]+e*h;
                      q[v]=e*q[v]-s*h;
                    }
                }
              c[j]=s*p; b[j]=e*p;
            }
          while (fabs(c[j])>d);
        }
      b[j]=b[j]+f;
    }
  for (i=0; i<=n-1; i++)
    { k=i; p=b[i];
      if (i+1<=n-1)
        { j=i+1;
          while ((j<=n-1)&&(b[j]<=p))
            { k=j; p=b[j]; j=j+1;}
        }
      if (k!=i)
        { b[k]=b[i]; b[i]=p;
          for (j=0; j<=n-1; j++)
            { u=j*n+i; v=j*n+k;
              p=q[u]; q[u]=q[v]; q[v]=p;
            }
        }
    }
  return(1);
}
/////////////////////////////////////////////////////////////
void chhbg(double a[],int n)
{ int i,j,k,u,v;
  double d,t;
  for (k=1; k<=n-2; k++)
    { d=0.0;
      for (j=k; j<=n-1; j++)
        { u=j*n+k-1; t=a[u];
          if (fabs(t)>fabs(d))
            { d=t; i=j;}
        }
      if (fabs(d)+1.0!=1.0)
        { if (i!=k)
            { for (j=k-1; j<=n-1; j++)
                { u=i*n+j; v=k*n+j;
                  t=a[u]; a[u]=a[v]; a[v]=t;
                }
              for (j=0; j<=n-1; j++)
                { u=j*n+i; v=j*n+k;
                  t=a[u]; a[u]=a[v]; a[v]=t;
                }
            }
          for (i=k+1; i<=n-1; i++)
            { u=i*n+k-1; t=a[u]/d; a[u]=0.0;
              for (j=k; j<=n-1; j++)
                { v=i*n+j;
                  a[v]=a[v]-t*a[k*n+j];
                }
              for (j=0; j<=n-1; j++)
                { v=j*n+k;
                  a[v]=a[v]+t*a[j*n+i];
                }
            }
        }
    }
  return;
}
/////////////////////////////////////////////////////////////
int cjcbi(double a[],int n,double v[],double eps,int jt)
{ int i,j,p,q,u,w,t,s,l;
  double fm,cn,sn,omega,x,y,d;
  l=1;
  for (i=0; i<=n-1; i++)
    { v[i*n+i]=1.0;
      for (j=0; j<=n-1; j++)
        if (i!=j) v[i*n+j]=0.0;
    }
  while (1==1)
    { fm=0.0;
      for (i=1; i<=n-1; i++)
      for (j=0; j<=i-1; j++)
        { d=fabs(a[i*n+j]);
          if ((i!=j)&&(d>fm))
            { fm=d; p=i; q=j;}
        }
      if (fm<eps)  return(1);
      if (l>jt)  return(-1);
      l=l+1;
      u=p*n+q; w=p*n+p; t=q*n+p; s=q*n+q;
      x=-a[u]; y=(a[s]-a[w])/2.0;
      omega=x/sqrt(x*x+y*y);
      if (y<0.0) omega=-omega;
      sn=1.0+sqrt(1.0-omega*omega);
      sn=omega/sqrt(2.0*sn);
      cn=sqrt(1.0-sn*sn);
      fm=a[w];
      a[w]=fm*cn*cn+a[s]*sn*sn+a[u]*omega;
      a[s]=fm*sn*sn+a[s]*cn*cn-a[u]*omega;
      a[u]=0.0; a[t]=0.0;
      for (j=0; j<=n-1; j++)
      if ((j!=p)&&(j!=q))
        { u=p*n+j; w=q*n+j;
          fm=a[u];
          a[u]=fm*cn+a[w]*sn;
          a[w]=-fm*sn+a[w]*cn;
        }
      for (i=0; i<=n-1; i++)
        if ((i!=p)&&(i!=q))
          { u=i*n+p; w=i*n+q;
            fm=a[u];
            a[u]=fm*cn+a[w]*sn;
            a[w]=-fm*sn+a[w]*cn;
          }
      for (i=0; i<=n-1; i++)
        { u=i*n+p; w=i*n+q;
          fm=v[u];
          v[u]=fm*cn+v[w]*sn;
          v[w]=-fm*sn+v[w]*cn;
        }
    }
  return(1);
}
/////////////////////////////////////////////////////////////
void cjcbj(double a[],int n,double v[],double eps)
{ int i,j,p,q,u,w,t,s;
  double ff,fm,cn,sn,omega,x,y,d;
  for (i=0; i<=n-1; i++)
    { v[i*n+i]=1.0;
      for (j=0; j<=n-1; j++)
        if (i!=j) v[i*n+j]=0.0;
    }
  ff=0.0;
  for (i=1; i<=n-1; i++)
  for (j=0; j<=i-1; j++)
    { d=a[i*n+j]; ff=ff+d*d; }
  ff=sqrt(2.0*ff);
  loop0:
  ff=ff/(1.0*n);
  loop1:
      for (i=1; i<=n-1; i++)
      for (j=0; j<=i-1; j++)
        { d=fabs(a[i*n+j]);
          if (d>ff)
            { p=i; q=j;
              goto loop;
            }
        }
      if (ff<eps) return;
      goto loop0;
loop: u=p*n+q; w=p*n+p; t=q*n+p; s=q*n+q;
      x=-a[u]; y=(a[s]-a[w])/2.0;
      omega=x/sqrt(x*x+y*y);
      if (y<0.0) omega=-omega;
      sn=1.0+sqrt(1.0-omega*omega);
      sn=omega/sqrt(2.0*sn);
      cn=sqrt(1.0-sn*sn);
      fm=a[w];
      a[w]=fm*cn*cn+a[s]*sn*sn+a[u]*omega;
      a[s]=fm*sn*sn+a[s]*cn*cn-a[u]*omega;
      a[u]=0.0; a[t]=0.0;
      for (j=0; j<=n-1; j++)
      if ((j!=p)&&(j!=q))
        { u=p*n+j; w=q*n+j;
          fm=a[u];
          a[u]=fm*cn+a[w]*sn;
          a[w]=-fm*sn+a[w]*cn;
        }
      for (i=0; i<=n-1; i++)
        if ((i!=p)&&(i!=q))
          { u=i*n+p; w=i*n+q;
            fm=a[u];
            a[u]=fm*cn+a[w]*sn;
            a[w]=-fm*sn+a[w]*cn;
          }
      for (i=0; i<=n-1; i++)
        { u=i*n+p; w=i*n+q;
          fm=v[u];
          v[u]=fm*cn+v[w]*sn;
          v[w]=-fm*sn+v[w]*cn;
        }
     goto loop1;
}
/////////////////////////////////////////////////////////////
#endif

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -