Folks,
I'm having a bit of trouble trying to understand why my code won't work. I've created a macro in order to carry out two different processes depending on the time period.
Basically what I have is a datasource based of survey response and one based off administrative data.
However, not all the individuals who are in the survey are actually in the administrative data set.
Therefore what I would like to do is stack on my missing individuals to my dataset to have a hybrid of survey values(when we can't find the person on the admin dataset) and admin values(when the person is on the admin dataset).
Depending on the year there is a need to call on different datasets. Therefore, I've created this macro.
However, I'm having issue getting it to run. Any input would be great. Perhaps I'm missing %end statment somwhere or something?
Any help would be great.
%macro nonadmin;
%if year = 2011 %to 2013 %then %do;
data survey_&year(rename=(sex=sex1));
set mywork.combined_sample_&year_7;
run;
data admin_&year(keep=gender calc person_id sex agen);
set mywork.combined_sample_&year._7;
run;
proc sort data= survey_&year; by person_id;
proc sort data= admin_&year; by person_id;
data combine_&year;
set ssurvey_&year admin_&year;
by person_id;
if first.person_id and last.person_id then output
run;
%end;
%else %if year = 2014 %to 2015 %then %do;
data survey_&year(rename=(sex=sex1));
set finaldat.survey&year;
run;
data admin_&year(keep=gender calc person_id sex agen);
set mywork.combined_sample_&year._7;
run;
proc sort data= survey_&year; by person_id;
proc sort data= admin_&year; by person_id;
data combine_&year;
set survey_&year admin_&year;
by person_id;
if first.person_id and last.person_id then output ;
run;
%end;
%mend nonadmin;
%if year = 2011 %to 2013 %then %do;
The text(!) "year" can never be equal to the text "2011".
That the %to in a condition does not throw an error baffles me, I must say. AFAIK, %to is only usable in a iterative %do statement.
You probably wanted something along the line
options minoperator;
%macro nonadmin(year) / mindelimiter=',';
%if &year in 2011,2012,2013 %then %do;
Kurt,
Do you mean something like this?
%macro nonadmin(year) / mindelimiter=',';
%if &year in 2011,2012,2013 %then %do;
data survey_&year(rename=(sex=sex1));
set mywork.combined_sample_&year_7;
run;
data admin_&year(keep=gender calc person_id sex agen);
set mywork.combined_sample_&year._7;
run;
proc sort data= survey_&year; by person_id;
proc sort data= admin_&year; by person_id;
data combine_&year;
set ssurvey_&year admin_&year;
by person_id;
if first.person_id and last.person_id then output
run;
%end;
%else %if &year in 2014,2015 %then %do;
data survey_&year(rename=(sex=sex1));
set finaldat.survey&year;
run;
data admin_&year(keep=gender calc person_id sex agen);
set mywork.combined_sample_&year._7;
run;
proc sort data= survey_&year; by person_id;
proc sort data= admin_&year; by person_id;
data combine_&year;
set survey_&year admin_&year;
by person_id;
if first.person_id and last.person_id then output ;
run;
%end;
%mend nonadmin;
%nonadmin (2011);
%nonadmin (2012);
%nonadmin (2013);
%nonadmin (2014);
%nonadmin (2015);When I run this I get the following error,
ERROR: A character operand was found in the %EVAL function or %IF condition where a numeric operand is required. The condition was:
&year in 2011,2012,2013
ERROR: The macro NONADMIN will stop executing.Utilising Macro's are all fairly new to me but I appreciate any input.
You missed to set the option I gave you:
*options minoperator;
%macro nonadmin(year) / mindelimiter=',';
%if &year in 2011,2012,2013 %then %do;
%put the value was found;
%end;
%mend;
%nonadmin(2011)
results in
24 *options minoperator;
25 %macro nonadmin(year) / mindelimiter=',';
26 %if &year in 2011,2012,2013 %then %do;
27 %put the value was found;
28 %end;
29 %mend;
30 %nonadmin(2011)
ERROR: A character operand was found in the %EVAL function or %IF condition where a numeric operand is required. The condition was:
&year in 2011,2012,2013
ERROR: The macro NONADMIN will stop executing.
but
options minoperator;
%macro nonadmin(year) / mindelimiter=',';
%if &year in 2011,2012,2013 %then %do;
%put the value was found;
%end;
%mend;
%nonadmin(2011)
results in
24 options minoperator; 25 %macro nonadmin(year) / mindelimiter=','; 26 %if &year in 2011,2012,2013 %then %do; 27 %put the value was found; 28 %end; 29 %mend; 30 %nonadmin(2011) the value was found
Would it not be simpler to put the data together, then do the processing?
data total_survey; set survey: indsname=tmp; year=scan(tmp,2,"_"); run; data total_admin; set admin: indsname=tmp; year=scan(tmp,2,"_"); run;
Its just a matter of changing the set statements to be for your data. The you have a total of each datasets to work with, avoids all the looping.
April 27 – 30 | Gaylord Texan | Grapevine, Texas
Walk in ready to learn. Walk out ready to deliver. This is the data and AI conference you can't afford to miss.
Register now and lock in 2025 pricing—just $495!
Check out this tutorial series to learn how to build your own steps in SAS Studio.
Find more tutorials on the SAS Users YouTube channel.
Ready to level-up your skills? Choose your own adventure.