Date: Fri, 24 Sep 2010 12:56:59 -0400
Reply-To: Ian Whitlock <iw1sas@GMAIL.COM>
Sender: "SAS(r) Discussion" <SAS-L@LISTSERV.UGA.EDU>
From: Ian Whitlock <iw1sas@GMAIL.COM>
Subject: Re: Using retain
Content-Type: text/plain; charset=ISO-8859-1
Summary: Example data has to be general enough to show the problem.
If you want to do something with the last value of type,
then you have to know the value of last type.
#iw-value=1
SAS Quest,
Part of the problem is not giving a sufficiently general example.
Suppose the data looks like:
data have;
input sub type$ val;
cards;
1 A 20
1 A 30
1 A 36
1 A 41
1 B 1
1 B 5
1 B 11
1 B 19
2 A 12
2 A 20
2 A 29
2 A 31
2 B 3
2 B 10
2 B 11
2 C 7
2 C 30
run;
What do you want as a result? It could be that this is too general.
Perhaps all SUBS have precisely the same TYPES. Simplifying Art's
code and complicating it with getting information ahead of time.
There are are two possibilities depending on what you want.
1) Same types in all SUBs.
data _null_ ;
set have ;
by sub ;
if last.sub ;
call symput ( "lasttype" , type ) ;
stop;
run ;
data want;
set have;
if type ^= &lasttype then do;
val_=val;
n_val=val;
end;
else n_val+val;
run;
2) Any SUB can have any TYPEs.
data cntl ( keep = sub lasttype ) ;
set have ;
by sub ;
if last.sub ;
lasttype = type ;
run ;
data want;
merge have cntl ;
by sub ;
if type ^= lasttype then do;
val_=val;
n_val=val;
end;
else n_val+val;
run;
Note the second version works with either interpretation, but
the first is more efficient when it is appropriate, becasue
there is less IO done.
Ian Whitlock
===============
Date: Fri, 24 Sep 2010 10:36:59 -0400
From: Sas Quest <sasquest@GMAIL.COM>
Subject: Using retain
data have;
input sub type$ val;
cards;
1 A 20
1 A 30
1 A 36
1 A 41
1 B 1
1 B 5
1 B 11
1 B 19
2 A 12
2 A 20
2 A 29
2 A 31
2 B 3
2 B 10
2 B 11
run;
Want:
Sub type val n_val
1 A 20 20
1 A 30 30
1 A 36 36
1 A 41 41
1 B 1 42
1 B 5 46
1 B 11 52
1 B 19 60
2 A 12 12
2 A 20 20
2 A 29 29
2 A 31 31
2 B 3 34
2 B 10 41
2 B 11 42
my code:
data want;
set have;
by sub type;
retain val_ 0;
n_val=val_+val;
/*f=first.type;
l=last.type;*/
if last.type then val_=val;
drop val_;
run;
What can be modified in my code to get the desired output?
Thanks