Mercurial > hg > jgplsrc
view vgauss.c @ 0:e0bbaa717f41 draft default tip
lol J
author | Jordi Gutiérrez Hermoso <jordigh@octave.org> |
---|---|
date | Mon, 25 Nov 2013 11:56:30 -0500 |
parents | |
children |
line wrap: on
line source
/* Copyright 1990-2011, Jsoftware Inc. All rights reserved. */ /* License in license.txt. */ /* */ /* Verbs: Gaussian Elimination */ #include "j.h" F1(jtgausselm){A t;C*tv;I c,e,i,j,m,old,r,r1,*s;Q p,*u,*v,*x; F1RANK(2,jtgausselm,0); ASSERT(RAT&AT(w),EVNONCE); ASSERT(2==AR(w),EVRANK); s=AS(w); r=s[0]; c=s[1]; r1=MIN(r,c); v=QAV(w); m=c*bp(AT(w)); GA(t,LIT,m,1,0); tv=CAV(t); old=jt->tbase+jt->ttop; for(j=0;j<r1;++j){ e=-1; u=v+c*j+j; DO(r-j, if(XDIG(u->n)){e=i+j; break;} u+=c;); /* find pivot row */ ASSERT(0<=e,EVDOMAIN); x=v+c*j; if(j!=e){u=v+c*e; MC(tv,x,m); MC(x,u,m); MC(u,tv,m);} /* interchange rows e and j */ p=x[j]; DO(c, x[i]=qdiv(x[i],p);); for(i=0;i<r;++i){ if(i==j)continue; u=v+c*i; p=u[j]; /* pivot */ DO(c, u[i]=qminus(u[i],qtymes(p,x[i]));); } gc(w,old); } R w; } /* Gaussian elimination in place */ static F1(jtdetr){A t,z;C*tv;I c,e,g=1,i,j,k,m,old,r,*s;Q d,p,*u,*v,*x; RZ(w); s=AS(w); r=s[0]; c=s[1]; v=QAV(w); m=c*sizeof(Q); GA(t,LIT,m,1,0); tv=CAV(t); old=jt->tbase+jt->ttop; for(j=0;j<r;++j){ e=-1; u=v+c*j+j; DO(r-j, if(XDIG(u->n)){e=i+j; break;} u+=c;); /* find pivot row */ if(0>e)R cvt(RAT,zero); x=v+c*j; if(j!=e){u=v+c*e; MC(tv,x,m); MC(x,u,m); MC(u,tv,m); g=-g;} /* interchange rows e and j */ i=XDIG(x[j].n); if(i==XPINF||i==XNINF)R mark; for(i=j+1;i<r;++i){ u=v+c*i; if(XDIG(u[j].n)){p=qdiv(u[j],x[j]); for(k=j+1;k<r;++k)u[k]=qminus(u[k],qtymes(p,x[k]));} } gc(w,old); } d=0<g?*v:qminus(zeroQ,*v); u=v+1+c; DO(r-1, d=qtymes(d,*u); u+=1+c;); RE(0); GA(z,RAT,1,0,0); *QAV(z)=d; R z; } /* determinant on rational matrix; works in place */ static F1(jtdetd){D g,h,p,q,*u,*v,*x,*y,z=1.0;I c,d,e,i,j,k,r,*s; RZ(w); s=AS(w); r=s[0]; c=s[1]; v=DAV(w); NAN0; for(j=0;j<r;++j){ x=v+c*j; u=x+j; h=0.0; DO(r-j, k=i; DO(c-j, g=ABS(*u); if(h<g){h=g; d=j+k; e=j+i;} ++u;); u+=j;); /* find pivot, maximum abs element */ if(h==inf)R mark; if(0==h)R scf(0.0); if(j!=d){u=v+c*d+j; y=x+j; DO(c-j, q=*u; *u=*y; *y=q; ++u; ++y; ); z=-z;} /* interchange rows j and d */ if(j!=e){u=x+e; y=x+j; DO(r-j, q=*u; *u=*y; *y=q; u+=c; y+=c;); z=-z;} /* interchange cols j and e */ q=x[j]; z*=q; JBREAK0; for(i=j+1;i<r;++i){ u=v+c*i; if(u[j]){p=u[j]/q; for(k=j+1;k<r;++k)u[k]-=p*x[k];} }} NAN1; R scf(z); } /* determinant on real matrix; works in place */ #define ZABT(v) ((v).re*(v).re+(v).im*(v).im) static F1(jtdetz){A t;D g,h;I c,d,e,i,j,k,r,*s;Z p,q,*u,*v,*x,*y,z; RZ(w); z.re=1.0; z.im=0.0; s=AS(w); r=s[0]; c=s[1]; v=ZAV(w); NAN0; for(j=0;j<r;++j){ x=v+c*j; u=x+j; h=0.0; DO(r-j, k=i; DO(c-j, g=ZABT(*u); if(h<g){h=g; d=j+k; e=j+i;} ++u;); u+=j;); /* find pivot, maximum abs element */ if(h==inf)R mark; if(0==h)R scf(0.0); if(j!=d){u=v+c*d; DO(c-j, q=u[j+i]; u[j+i]=x[j+i]; x[j+i]=q;); z=zminus(zeroZ,z);} /* interchange rows j and d */ if(j!=e){u=v+c*j+e; y=v+c*j+j; DO(r-j, q=*u; *u=*y; *y=q; u+=c; y+=c;); z=zminus(zeroZ,z);} /* interchange cols j and e */ q=x[j]; z=ztymes(z,q); for(i=j+1;i<r;++i){ u=v+c*i; if(ZNZ(u[j])){p=zdiv(u[j],q); for(k=j+1;k<r;++k)u[k]=zminus(u[k],ztymes(p,x[k]));} }} NAN1; RE(0); GA(t,CMPX,1,0,0); *ZAV(t)=z; R t; } /* determinant on complex matrix; works in place */ F1(jtgaussdet){A z;I*s; RZ(w); ASSERT(2==AR(w),EVRANK); s=AS(w); ASSERT(s[0]==s[1],EVLENGTH); switch(AT(w)){ default: ASSERT(0,EVDOMAIN); case B01: case INT: R detd(cvt(FL,w)); case FL: z=detd(ca(w)); break; case CMPX: z=detz(ca(w)); break; case XNUM: z=detr(cvt(RAT,w)); break; case RAT: z=detr(ca(w)); } R z==mark?detxm(w,eval("-/ .*")):z; } /* determinant on square matrix */