Hello,
I have this data;
data test;
input id $ val;
cards;
A .
A .
A .
A 5
A .
A 6
B .
B .
B .
B 4
B .
B .
B 7
; run;
I want this result :
data test;
input id $ val;
cards;
A 5
A 5
A 5
A 5
A 6
A 6
A 6
B 4
B 4
B 4
B 4
B 7
B 7
B 7
; run;
How i can get this result?
Thank you for your help
Here's one approach (assuming you fix the number of observations in your example):
data want;
do until (last.id or val > .) ;
set have;
by id;
end;
replacement_val = val;
do until (last.id or val > .) ;
set have;
by id;
output;
end;
drop val;
rename replacement_val = val;
run;
The bottom loop reads the same observations as the top loop, but has an additional variable to work with as it outputs observations.
I am not quite sure I understand. There are more observations in the second list than in the first one.
If you wanted to carry over the value of val for all missing entries until you get to a new value and then carry that value on until a new value etc you could use the RETAIN statement but it would require careful ordering of the data.
Without another variable to distinguish the observation other than id it will be tricky to assign different values to the same id value.
Here's one approach (assuming you fix the number of observations in your example):
data want;
do until (last.id or val > .) ;
set have;
by id;
end;
replacement_val = val;
do until (last.id or val > .) ;
set have;
by id;
output;
end;
drop val;
rename replacement_val = val;
run;
The bottom loop reads the same observations as the top loop, but has an additional variable to work with as it outputs observations.
thank you for your reply.
I can't visualize the process of treatment including the ability of the program to change the value of replacement_val at the right time.
I know that the condition (or val>.) Has a role.
Thanks again
Here are some of the initial steps, to get you thinking about the process correctly.
This version of the program never copies VAL from the previous ID. It always begins again when it finds a new ID. I assumed that's what you wanted, but could be wrong about that.
Good.
Thank you
Based on the presented data, looks like by-processing is not required, so your code could be reduced to:
data want;
do until (val > .) ;
set have;
end;
replacement_val = val;
do until (val > .) ;
set have;
output;
end;
drop val;
rename replacement_val = val;
run;
Amir.
Here's a different approach that only reads the input data once
data test;
input id $ val;
cards;
A .
A .
A .
A 5
A .
A 6
B .
B .
B .
B 4
B .
B .
B 7
; run;
data want ;
retain cntr 0 ;
set test ;
cntr+1 ;
if val ne . then do ;
do i=1 to cntr ;
output want ;
end ;
cntr=0 ;
end ;
run ;
It counts the number of observations that have a missing value, and then when it gets to an obs that has a value it writes to the output dataset, and resets the counter (cntr)
Registration is now open for SAS Innovate 2025 , our biggest and most exciting global event of the year! Join us in Orlando, FL, May 6-9.
Sign up by Dec. 31 to get the 2024 rate of just $495.
Register now!
Learn how use the CAT functions in SAS to join values from multiple variables into a single value.
Find more tutorials on the SAS Users YouTube channel.
Ready to level-up your skills? Choose your own adventure.