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 (May 2000, week 1)Back to main SAS-L pageJoin or leave SAS-L (or change settings)ReplyPost a new messageSearchProportional fontNon-proportional font
Date:         Sat, 6 May 2000 19:11:45 GMT
Reply-To:     sashole@mediaone.net
Sender:       "SAS(r) Discussion" <SAS-L@LISTSERV.UGA.EDU>
From:         Paul Dorfman <paul_dorfman@HOTMAIL.COM>
Subject:      Re: computing difference between observations in a by group
Comments: To: icj808@USWEST.NET
Content-Type: text/plain; format=flowed

Paula,

OK, that makes it much more transparent. You have a file MOM like

ID V22 ------ 1 4 1 5 1 4 3 1 3 7 5 6 5 8 5 3 6 1 6 1 7 9 7 0 9 3 9 1 9 5

and want to create 3 files SAME, INCR, DECR depending on the relationship between V22 in the first and last records in each ID group. Now, there are 2 possible variants: 1) you want the output files to contain the _entire_ qualifying groups, that is, you want them to look like

SAME INCR DECR ------ ------ ------ ID V22 ID V22 ID V22 ------ ------ ------ 1 4 3 1 5 6 1 5 3 7 5 8 1 4 9 3 5 3 6 1 9 1 7 9 6 1 9 5 7 0

2) you want only qualifying IDs:

SAME INCR DECR ---- ---- ---- ID ID ID ---- ---- ---- 1 3 5 6 9 7

The task #2 is simple:

data same incr decr; keep id; set mom; by id; retain fv22; if first.id then fv22 = v22; if last.id then select; when (v22 > fv22) output incr; when (v22 < fv22) output decr; otherwise output same; end; run;

The same can be accomplished shorter in 'retainless' form by enclosing each by-group in an explicit loop:

data same incr decr; do until (last.id); set mom; by id; if first.id then fv22 = v22; end; if v22 > fv22 then output incr; else if v22 < fv22 then output decr; else output same; keep id; run;

Here RETAIN is unnecessary, because during the process of reading a by-group, the bottom of the step is never reached, and therefore FV22 retains the same value for all iterations. When the group is done, the value of V22 sitting in memory is the one from the bottom of the group and is compared to FV22 acquired at the top. Only then FV22 is set to missing, control is transferred to the top of the step, and processing of the next group commences.

If you need the task #2 accomplished also, you now have everything you need:

data same incr decr; merge mom(in=m) same(in=s) incr(in=i) decr(in=d); by id; if m; if s then output same; else if i then output incr; else if d then output decr; run;

Principally, #2 can be done in a single pass over MOM, but it requires some look-ahead logic - you have to store a by-group somewhere before you know that the last value in the group is. There is a variety of interesting ways to do that, however, I am not sure it fits the thread.

Kind regards, ====================== Paul M. Dorfman Jacksonville, FL ======================

>From: paula <icj808@USWEST.NET>

>Let me take Paul's advice and clarify what I want to accomplish here. > >I am trying to generate 4 baby sas data sets from a single mother data set, >increase, decrease, nochange, and change. The criteron, as you may have >known, is to see if the last value of V22 for a specific ID value is >greater, less than, or equal to the first value of V22 for the same ID >value. When this process is complete, the mother set remains intact. > >For example, for ID=1, since 35> 33, Id=1 belongs to Increase. For ID=2, >since 30<39, it goes to Decrease, and so on.

________________________________________________________________________ Get Your Private, Free E-mail from MSN Hotmail at http://www.hotmail.com


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