Here is my data:
ID_Number | year | jan | feb | mar | apr | may | jun | jul | aug | sep | oct | nov | dec |
1 | 2018 | 0 | 0 | 0 | 1 | 1 | 0 | 0 | 0 | 0 | 0 | 0 | 1 |
1 | 2019 | 1 | 1 | 1 | 1 | 1 | 1 | 1 | 1 | 1 | 1 | 1 | 1 |
2 | 2018 | 1 | 1 | 0 | 0 | 1 | 1 | 1 | 1 | 1 | 1 | 1 | 1 |
2 | 2019 | 1 | 1 | 1 | 1 | 1 | 1 | 0 | 0 | 0 | 0 | 0 | 0 |
An ID qualifies to be selected if they were a member 90 days before and after an event.
If both ID's had an event in Feb 2019 (20190215) which ID number(s) would be selected?
In response to a question - there is an event table containing ID and Event_date YYYYMMDD.
thank you
Note: (I would expect only ID 2 would be selected)
This filters the 1s:
if m{month}
A zero causes this to be false.
Since your membership table has only months, the precise dates become irrelevant, so I align everything to the first of a month, first when transposing the dataset, and next when calculating the time window with INTNX.
So, how do we know when an "event" occurs???
First of all, make your data intelligent by transposing to a long format, and making SAS dates.
Then you can use a simple join to find your answer.
data long;
set have;
array m {12} jan--dec;
do month = 1 to 12;
if m{month)
then do;
mem_month = mdy(month,1,year);
output;
end;
end;
keep id_number mem_month;
run;
data want;
merge
long
have_event
;
by id_number;
if event_date - mem_month le 90 then output;
run;
So instead of just finding one observation in the span, we need to count if 7 observations can be found.
An we need to take care of 3-month intervals, which are usually not 90 days.
See this complete and tested code:
data have;
input ID_Number $ year jan feb mar apr may jun jul aug sep oct nov dec;
datalines;
1 2018 0 0 0 1 1 0 0 0 0 0 0 1
1 2019 1 1 1 1 1 1 1 1 1 1 1 1
2 2018 1 1 0 0 1 1 1 1 1 1 1 1
2 2019 1 1 1 1 1 1 0 0 0 0 0 0
;
data have_event;
input id_number $ event_date :yymmdd8.;
format event_date yymmdd10.;
datalines;
1 20190215
2 20190215
;
data long;
set have;
array m {12} jan--dec;
do month = 1 to 12;
if m{month}
then do;
mem_month = mdy(month,1,year);
output;
end;
end;
format mem_month yymmdd10.;
keep id_number mem_month;
run;
data want;
merge
long
have_event
;
by id_number;
if first.id_number then counter = 0;
if intnx('month',event_date,-3,"b") le mem_month le intnx('month',event_date,3,'b') then counter + 1;
if last.id_number;
if counter ge 7
then flag = 1;
else flag = 0;
keep id_number flag;
run;
proc print data=want noobs;
run;
Result:
ID_Number flag 1 0 2 1
If you comment the KEEP statement, you will see that the counter is 6 and 7, respectively.
This filters the 1s:
if m{month}
A zero causes this to be false.
Since your membership table has only months, the precise dates become irrelevant, so I align everything to the first of a month, first when transposing the dataset, and next when calculating the time window with INTNX.
SAS Innovate 2025 is scheduled for May 6-9 in Orlando, FL. Sign up to be first to learn about the agenda and registration!
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.