/* conjugate gradient solver for symmetric positive definite systems from Handbook of C tools for Scientists and Engineers by L. Baker int cgs() returns integer count of iterations used. main() is test driver for spd system. As system is of second order, two iterations should produce "exact" answer (neglecting roundoff). DEPENDENCIES: requires routines in vector.c */ #include int cgs(a,x,y,r,p,ar,ap,n,m,xold) int n,m; float a[],x[],y[],r[],p[],ar[],ap[],xold[]; { float gamma,rnew,alpha,beta,rlen; float resid; double dot(); int i,k; int j; vset(x,0.,n); vcopy(y,r,n); vcopy (x,xold,n); beta=0.; vcopy(r,p,n); pv(x,n); pv(r,n); pv(p,n); k=n<<1; DOFOR(i,k) { /* ith iteration*/ mv(a,p,ap,n,n); /* pv(ap,n);*/ alpha=dot(p,ap,n); rlen=dot(r,r,n); if(alpha==0. || rlen==0.) return(i); alpha=rlen/alpha; /*update*/ vv(x,x,p,alpha,n); gamma=-alpha; vv(r,r,ap,gamma,n); rnew=dot(r,r,n); beta=rnew/rlen; if(beta==0.)return(-i); vv(p,r,p,beta,n); /* pv(p,n); */ for(j=0,resid=0.;j