123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258 |
- #include <grass/gis.h>
- #include <math.h>
- static double at,bt,ct;
- #define PYTHAG(a,b) ((at=fabs(a)) > (bt=fabs(b)) ? \
- (ct=bt/at,at*sqrt(1.0+ct*ct)) : (bt ? (ct=at/bt,bt*sqrt(1.0+ct*ct)): 0.0))
- static double maxarg1,maxarg2;
- #define MAX(a,b) (maxarg1=(a),maxarg2=(b),(maxarg1) > (maxarg2) ?\
- (maxarg1) : (maxarg2))
- #define SIGN(a,b) ((b) >= 0.0 ? fabs(a) : -fabs(a))
- int G_svdcmp( double **a, int m,int n, double *w,double **v)
- {
- int flag,i,its,j,jj,k,ii=0,nm=0;
- double c,f,h,s,x,y,z;
- double anorm=0.0,g=0.0,scale=0.0;
- double *rv1,*G_alloc_vector();
- if (m < n) return -1; /* must augment A with extra zero rows */
- rv1=G_alloc_vector(n);
- n--;
- m--;
- for (i=0;i<=n;i++) {
- ii=i+1;
- rv1[i]=scale*g;
- g=s=scale=0.0;
- if (i <= m) {
- for (k=i;k<=m;k++) scale += fabs(a[k][i]);
- if (scale) {
- for (k=i;k<=m;k++) {
- a[k][i] /= scale;
- s += a[k][i]*a[k][i];
- }
- f=a[i][i];
- g = -SIGN(sqrt(s),f);
- h=f*g-s;
- a[i][i]=f-g;
- if (i != n) {
- for (j=ii;j<=n;j++) {
- for (s=0.0,k=i;k<=m;k++) s += a[k][i]*a[k][j];
- f=s/h;
- for (k=i;k<=m;k++) a[k][j] += f*a[k][i];
- }
- }
- for (k=i;k<=m;k++) a[k][i] *= scale;
- }
- }
- w[i]=scale*g;
- g=s=scale=0.0;
- if (i <= m && i != n) {
- for (k=ii;k<=n;k++) scale += fabs(a[i][k]);
- if (scale) {
- for (k=ii;k<=n;k++) {
- a[i][k] /= scale;
- s += a[i][k]*a[i][k];
- }
- f=a[i][ii];
- g = -SIGN(sqrt(s),f);
- h=f*g-s;
- a[i][ii]=f-g;
- for (k=ii;k<=n;k++) rv1[k]=a[i][k]/h;
- if (i != m) {
- for (j=ii;j<=m;j++) {
- for (s=0.0,k=ii;k<=n;k++) s += a[j][k]*a[i][k];
- for (k=ii;k<=n;k++) a[j][k] += s*rv1[k];
- }
- }
- for (k=ii;k<=n;k++) a[i][k] *= scale;
- }
- }
- anorm=MAX(anorm,(fabs(w[i])+fabs(rv1[i])));
- }
- for (i=n;i>=0;i--) {
- if (i < n) {
- if (g) {
- for (j=ii;j<=n;j++)
- v[j][i]=(a[i][j]/a[i][ii])/g;
- for (j=ii;j<=n;j++) {
- for (s=0.0,k=ii;k<=n;k++) s += a[i][k]*v[k][j];
- for (k=ii;k<=n;k++) v[k][j] += s*v[k][i];
- }
- }
- for (j=ii;j<=n;j++) v[i][j]=v[j][i]=0.0;
- }
- v[i][i]=1.0;
- g=rv1[i];
- ii=i;
- }
- for (i=n;i>=0;i--) {
- ii=i+1;
- g=w[i];
- if (i < n)
- for (j=ii;j<=n;j++) a[i][j]=0.0;
- if (g) {
- g=1.0/g;
- if (i != n) {
- for (j=ii;j<=n;j++) {
- for (s=0.0,k=ii;k<=m;k++) s += a[k][i]*a[k][j];
- f=(s/a[i][i])*g;
- for (k=i;k<=m;k++) a[k][j] += f*a[k][i];
- }
- }
- for (j=i;j<=m;j++) a[j][i] *= g;
- } else {
- for (j=i;j<=m;j++) a[j][i]=0.0;
- }
- ++a[i][i];
- }
- for (k=n;k>=0;k--) {
- for (its=1;its<=30;its++) {
- flag=1;
- for (ii=k;ii>=0;ii--) {
- nm=ii-1;
- if (fabs(rv1[ii])+anorm == anorm) {
- flag=0;
- break;
- }
- if (fabs(w[nm])+anorm == anorm) break;
- }
- if (flag) {
- c=0.0;
- s=1.0;
- for (i=ii;i<=k;i++) {
- f=s*rv1[i];
- if (fabs(f)+anorm != anorm) {
- g=w[i];
- h=PYTHAG(f,g);
- w[i]=h;
- h=1.0/h;
- c=g*h;
- s=(-f*h);
- for (j=0;j<=m;j++) {
- y=a[j][nm];
- z=a[j][i];
- a[j][nm]=y*c+z*s;
- a[j][i]=z*c-y*s;
- }
- }
- }
- }
- z=w[k];
- if (ii == k) {
- if (z < 0.0) {
- w[k] = -z;
- for (j=0;j<=n;j++) v[j][k]=(-v[j][k]);
- }
- break;
- }
- if (its == 30) return -2; /*No convergence in 30 SVDCMP iterations*/
- x=w[ii];
- nm=k-1;
- y=w[nm];
- g=rv1[nm];
- h=rv1[k];
- f=((y-z)*(y+z)+(g-h)*(g+h))/(2.0*h*y);
- g=PYTHAG(f,1.0);
- f=((x-z)*(x+z)+h*((y/(f+SIGN(g,f)))-h))/x;
- c=s=1.0;
- for (j=ii;j<=nm;j++) {
- i=j+1;
- g=rv1[i];
- y=w[i];
- h=s*g;
- g=c*g;
- z=PYTHAG(f,h);
- rv1[j]=z;
- c=f/z;
- s=h/z;
- f=x*c+g*s;
- g=g*c-x*s;
- h=y*s;
- y=y*c;
- for (jj=0;jj<=n;jj++) {
- x=v[jj][j];
- z=v[jj][i];
- v[jj][j]=x*c+z*s;
- v[jj][i]=z*c-x*s;
- }
- z=PYTHAG(f,h);
- w[j]=z;
- if (z) {
- z=1.0/z;
- c=f*z;
- s=h*z;
- }
- f=(c*g)+(s*y);
- x=(c*y)-(s*g);
- for (jj=0;jj<=m;jj++) {
- y=a[jj][j];
- z=a[jj][i];
- a[jj][j]=y*c+z*s;
- a[jj][i]=z*c-y*s;
- }
- }
- rv1[ii]=0.0;
- rv1[k]=f;
- w[k]=x;
- }
- }
- G_free_vector(rv1);
- return 0;
- }
- #undef SIGN
- #undef MAX
- #undef PYTHAG
- int G_svbksb(
- double **u,double w[],double **v,
- int m,int n,double b[],double x[])
- {
- int j,i;
- double s,*tmp,*G_alloc_vector();
- tmp=G_alloc_vector(n);
- for (j=0;j<n;j++) {
- s=0.0;
- if (w[j]) {
- for (i=0;i<m;i++) s += u[i][j]*b[i];
- s /= w[j];
- }
- tmp[j]=s;
- }
- for (j=0;j<n;j++) {
- s=0.0;
- for (i=0;i<n;i++) s += v[j][i]*tmp[i];
- x[j]=s;
- }
- G_free_vector(tmp);
- return 0;
- }
- #define TOL 1e-8
- int G_svelim( double *w, int n)
- {
- int i;
- double thresh;
- thresh=0.0; /* remove singularity */
- for(i=0;i<n;i++)
- if (w[i] > thresh)
- thresh=w[i];
- thresh *= TOL;
- for(i=0;i<n;i++)
- if (w[i] < thresh)
- w[i]=0.0;
- return 0;
- }
- #undef TOL
|