LISTSERV at the University of Georgia
Menubar Imagemap
Home Browse Manage Request Manuals Register
Previous messageNext messagePrevious in topicNext in topicPrevious by same authorNext by same authorPrevious page (June 2002, week 1)Back to main SAS-L pageJoin or leave SAS-L (or change settings)ReplyPost a new messageSearchProportional fontNon-proportional font
Date:         Mon, 3 Jun 2002 03:00:46 -0700
Reply-To:     Ivan Bos <ivanlooptstage@HOTMAIL.COM>
Sender:       "SAS(r) Discussion" <SAS-L@LISTSERV.UGA.EDU>
From:         Ivan Bos <ivanlooptstage@HOTMAIL.COM>
Organization: http://groups.google.com/
Subject:      Re: Matrix multiplication without PROC IML
Content-Type: text/plain; charset=ISO-8859-1

Dear Armin,

I tried to use your macro, but a multiplication of a 4*4000 vs a 4000*4 matrix gave some problems:

>>>>>>>

WARNING: Argument 1 to function ATTRN referenced by the %SYSFUNC or %QSYSFUNC macro function is missing or out of range. ERROR: File WORK.XTRANS.DATA does not exist.

>>>>>>>

Do you know how to handle that problem?

Regards,

Ivan Bos Free University Amsterdam The Netherlands

Armin.Gemperli@UNIBAS.CH (Armin Gemperli) wrote in message news:<3CF4A421.8332576E@unibas.ch>... > Dear Ivan, > > I can see, you have the same Problem with your Boss as I have: It is > cheaper for him to let you program tedious matrix computation solutions > yourself, than buying IML. For the matrix-multiplication, I have added a > macro, but for the inversion stuff I should have more information about > the matrix to invert: Has it full rank/Generalized Inverse/Is it > positive-definite/symmetric etc. Because to programm your own solution > it helps a lot to use this ancillary information. > Cheers > Armin Gemperli > > > %MACRO MATMUL(A, B, C, COLNAME=COL); > /* ********************************************************* */ > /* Matrix multiplication A*B=C without using SAS/IML */ > /* ********************************************************* */ > /* */ > /* Parameters: */ > /* 1. First Matrix (A) */ > /* 2. Second Matrix (B), where the second dimension of A */ > /* and the first dimesnio of B must match (not checked)*/ > /* 3. Resulting Matrix (C) */ > /* 4. Colum Names of the resulting Matrix C. */ > /* Optional Argument, Default=COL */ > /* */ > /* ********************************************************* */ > OPTION NONOTES NOMPRINT; > %LET DATA=%sysfunc(OPEN(&A)); > %LET DIMLEFT=%sysfunc(ATTRN(&DATA,NOBS)); > %LET DIMJOIN=%sysfunc(ATTRN(&DATA,NVARS)); > %LET RC=%sysfunc(CLOSE(&DATA)); > %LET DATA=%sysfunc(OPEN(&B)); > %LET DIMCHECK=%sysfunc(ATTRN(&DATA,NOBS)); > %LET DIMRIGHT=%sysfunc(ATTRN(&DATA,NVARS)); > %LET MAT2VAR1=%SYSFUNC(VARNAME(&DATA,1)); > %LET MAT2VARN=%SYSFUNC(VARNAME(&DATA,&DIMRIGHT)); > %LET RC=%sysfunc(CLOSE(&DATA)); > %IF &DIMJOIN NE &DIMCHECK %THEN %DO; > %PUT ERROR: Dimensions do not match. Processing interrupted; > %GOTO EXIT; > %END; > PROC TRANSPOSE DATA=&A OUT=&C PREFIX=_AVAR_; > DATA &C (DROP=i j _AVAR_1-_AVAR_&DIMLEFT &MAT2VAR1--&MAT2VARN); > SET &C(DROP=_NAME_); > SET &B; > ARRAY _AARRAY {&DIMLEFT} _AVAR_1-_AVAR_&DIMLEFT; > ARRAY _BARRAY {&DIMRIGHT} &MAT2VAR1--&MAT2VARN; > ARRAY _CVAR_ {%EVAL(&DIMLEFT * &DIMRIGHT)}; > RETAIN _CVAR_; > IF _N_ EQ 1 THEN DO; > DO i=1 TO &DIMLEFT; > DO j=1 TO &DIMRIGHT; > _CVAR_((i-1)*&DIMRIGHT+j)=_AARRAY(i)*_BARRAY(j); > END; > END; > END; > ELSE DO; > DO i=1 TO &DIMLEFT; > DO j=1 TO &DIMRIGHT; > > _CVAR_((i-1)*&DIMRIGHT+j)=_CVAR_((i-1)*&DIMRIGHT+j)+_AARRAY(i)*_BARRAY(j); > END; > END; > END; > IF _N_ EQ &DIMJOIN THEN OUTPUT; > PROC TRANSPOSE DATA=&C OUT=&C PREFIX=_CVAR_; > DATA &C (DROP=i _CVAR_1); > SET &C(DROP=_NAME_); > ARRAY &COLNAME {&DIMRIGHT}; > RETAIN &COLNAME i 1; > &COLNAME(i)=_CVAR_1; > IF MOD(_N_,&DIMRIGHT) EQ 0 THEN DO; > OUTPUT; > i=1; > END; > ELSE i+1; > RUN; > /* *************** */ > /* ** EXAMPLES ** */ > /* *************** */ > /* > * _1_; > DATA A; > INPUT F G Z O Z65 R TTT; > datalines; > 1 2 0 4 66 11 8 > ; > DATA B; > INPUT R TTT; > DATALINES; > 6 6 > 0 1 > 1 0 > 8 345 > 9 5 > 0 88 > 111 9 > ; > RUN; > %MATMUL(A=A, B=B, C=C, COLNAME=V); > > * _2_; > DATA A; > INPUT A B C D ; > datalines; > 1 2 0 4 > 66 88 99 100 > 21 45 65 0 > 4 3 1 0.1 > ; > DATA B; > INPUT A B C; > DATALINES; > 0.1 0.1 0.11 > 99 0.9 0.0001 > 0.2 0 0.00001 > 100000 10.001 1.01 > ; > RUN; > %MATMUL(A,B,C); > */ > %EXIT: > OPTION NOTES; > %MEND MATMUL;


Back to: Top of message | Previous page | Main SAS-L page