Dear all,
I wanted to set up a macro to run quite a few logistic regression models. My question is how to I code it in such a way that
for the first 10 models, the macro would use bi as the dependent variable, for the next 10 models, use bi2 as the dependent variable etc.
The codes highlighted in purple wouldnt work.
%MACRO a;
%IF 1 <= &i <= 10 %THEN %DO; %LET &dep = bi; %END;
%IF 11 <= &i <= 20 %THEN %DO; %LET &dep = bi2; %END;
%IF 21 <= &i <= 30 %THEN %DO; %LET &dep = bi3; %END;
PROC LOGISTIC DATA = x;
MODEL &dep (REF = "Yes")= &indep;
RUN;
%MEND a;
%a(indep = mde, i = 1)
%a (indep = pds, i = 2)
%a (indep = pts, i = 3)
%a (indep = so, i = 4)
%a (indep = sp, i = 5)
:
%a(indep = pe, i = 30)
Any input is much appreciated. Thanks!
I can see several problems there.
Try it like this:
%MACRO a(indep=, i=);
%if %eval(&i >= 1 and &i <= 10)
%then %let dep = bi;
%else %if %eval(&i >= 11 and &i <= 20)
%then %let dep = bi2;
%else %if %eval(&i >= 21 and &i <= 30)
%then %let dep = bi3;
PROC LOGISTIC DATA = x;
MODEL &dep (REF = "Yes")= &indep;
RUN;
%MEND a;
The %eval isn't strictly necessary, but I always use it - it tends to pick up typing mistakes faster that I inevitably introduce to my code! I also like to use %else like this, where the conditions are mutually exclusive; sadly macro code doesn't have a %select statement. (Indentation like this not obligatory, of course…)
The %IF statement, really the implied %EVAL() function call, will not convert
A <= B <= C
into
(A<=B) and (B<=C)
like the IF statement will.
So you need to do that yourself.
I can see several problems there.
Try it like this:
%MACRO a(indep=, i=);
%if %eval(&i >= 1 and &i <= 10)
%then %let dep = bi;
%else %if %eval(&i >= 11 and &i <= 20)
%then %let dep = bi2;
%else %if %eval(&i >= 21 and &i <= 30)
%then %let dep = bi3;
PROC LOGISTIC DATA = x;
MODEL &dep (REF = "Yes")= &indep;
RUN;
%MEND a;
The %eval isn't strictly necessary, but I always use it - it tends to pick up typing mistakes faster that I inevitably introduce to my code! I also like to use %else like this, where the conditions are mutually exclusive; sadly macro code doesn't have a %select statement. (Indentation like this not obligatory, of course…)
Since you have control of &i as a parameter, you don't really need to safeguard against unusual values. You could simplify this to:
%if &i <= 10 %then %let dep = bi;
%else %if &i <= 20 then %let dep = bi2;
%else %let dep = bi3;
It's remotely possibly that the original %LET statements were correct. More likely, the %LET statements should assign a value to DEP (as illustrated above), not to &DEP (as in your original code).
Don't miss out on SAS Innovate - Register now for the FREE Livestream!
Can't make it to Vegas? No problem! Watch our general sessions LIVE or on-demand starting April 17th. Hear from SAS execs, best-selling author Adam Grant, Hot Ones host Sean Evans, top tech journalist Kara Swisher, AI expert Cassie Kozyrkov, and the mind-blowing dance crew iLuminate! Plus, get access to over 20 breakout sessions.
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.