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 (April 2003, week 3)Back to main SAS-L pageJoin or leave SAS-L (or change settings)ReplyPost a new messageSearchProportional fontNon-proportional font
Date:         Fri, 18 Apr 2003 18:37:04 +0000
Reply-To:     sashole@bellsouth.net
Sender:       "SAS(r) Discussion" <SAS-L@LISTSERV.UGA.EDU>
From:         Paul Dorfman <paul_dorfman@HOTMAIL.COM>
Subject:      Re: recoding variables
Comments: To: tyroc7@hotmail.com
Content-Type: text/plain; format=flowed

>From: L F <tyroc7@HOTMAIL.COM> > >I have a series of 16 variables let's call them relate1-relate16. I have >another variable called married. If any of the relate1-relate16 variables >has a value of 2 or a value of 11 I would like the married variable to take >on a value of 1. Otherwise the value of married should be 0. > >Can anyone recommend a succinct way of doing this without having to 16 >if/else statements?

LF,

In principle, the process can be made completely IF-less (R is short for Relate):

array r (16) ; married = index (peekc(addr(r1), dim(r)*8), put(02,rb8.)) | index (peekc(addr(r1), dim(r)*8), put(11,rb8.)) ;

If this is to be done in each of great many observations, it is better to compute much of the stuff once beforehand, for example:

220 data r ; 221 array r (7) ; 222 input r(*) ; 223 list ; 224 cards ;

RULE: ----+----1----+ 225 1 2 3 4 5 6 11 226 1 2 3 4 5 6 . 227 1 . 3 4 5 6 11 228 1 . 3 4 5 6 . 229 2 . 3 4 5 6 . 230 1 . 3 4 5 11 . 231 ; 232 run ; NOTE: The data set WORK.R has 6 observations and 7 variables.

233 234 data _null_ ; 235 array r (7) ; 236 rb02 = put (02, rb8.) ; 237 rb11 = put (11, rb8.) ; 238 a1 = addr (r1) ; 239 dimr = dim (r) ; 240 do until ( eof ) ; 241 set r end = eof ; 242 memstr = peekc (addr(r1), dimr * 8) ; 243 married = index (memstr, rb02) | index (memstr, rb11) ; 244 put (r(*)) (z2. +1) +1 married= ; 245 end ; 246 run ;

01 02 03 04 05 06 11 married=1 01 02 03 04 05 06 . married=1 01 . 03 04 05 06 11 married=1 01 . 03 04 05 06 . married=0 02 . 03 04 05 06 . married=1 01 . 03 04 05 11 . married=1

Jusge for yourself if the method is succinct enough or not. If not, you can process the array one element at a time, as others have indicated. I would also dare offer my own, more efficient, variant of this approach (input being the same):

387 run ; 388 389 data _null_ ; 390 array r (8) (8 * 2) ; *could code 11 instead ; 391 set r ; 392 do inx = 1 by 1 until ( r(inx) in (2, 11) ) ; 393 end ; 394 married = inx LE hbound(r) - 1 ; 395 put (r(*)) (z2. +1) +1 married= ; 396 run ;

01 02 03 04 05 06 11 02 married=1 01 02 03 04 05 06 . 02 married=1 01 . 03 04 05 06 11 02 married=1 01 . 03 04 05 06 . 02 married=0 02 . 03 04 05 06 . 02 married=1 01 . 03 04 05 11 . 02 married=1

I will let you (and others if they are interested) to ponder why the bodyless loop above (relying on the setinel located in the extra array item for stoppage) makes for higher computer efficiency.

Kind regards, ------------------- Paul M. Dorfman Jackonsville, FL -------------------

_________________________________________________________________ The new MSN 8: smart spam protection and 2 months FREE* http://join.msn.com/?page=features/junkmail


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