BookmarkSubscribeRSS Feed
🔒 This topic is solved and locked. Need further help from the community? Please sign in and ask a new question.
UniversitySas
Quartz | Level 8

Hello,

 

I'm currently trying to update a single-parameter macro, to two parameters.


The reason is that my initial macro creates a data-set, based on a certain summary statistic that I calculate inside the macro.

 

Now, I want to add a second parameter, that let's me call the macro and create a data-set based on a variety of summary statistics, but I am getting an error.

 

In my original macro, I have:

 

%MACRO create_Table1(y);

%DO i = 1 %TO 10;

*Table 1 Calculate 10th percentile;
PROC MEANS DATA = table_&y&i p10 noprint;
	BY year;
	VAR var_&y&i ;
	OUTPUT OUT = stat_&y&i P10(var_&y&i) = var_&y&i ;
RUN; 

*Insert more code that works fine;
%END
%MEND create_Table1;

%create_table(y1);

This works fine for me.

 

 

Now, I want it so that I can call the macro to calculate either p10 or p50, based on my parameters.

So I tried:

 

%MACRO create_Table1(y=, statistic=);

%DO i = 1 %TO 10;


*Table 1 Calculate 10th percentile if statistic = p10;

	%IF &statistic=p10 %THEN 
%DO;
PROC MEANS DATA = table_&y&i p10 noprint;
	BY year;
	VAR var_&y&i ;
	OUTPUT OUT = stat_&y&i P10(var_&y&i) = var_&y&i ;
RUN; 
%END;

*Table 2 Calculate 50th percentile if statistic = p50;
	%ELSE %IF &statistic=p50 %THEN 
%DO;
PROC MEANS DATA = table_&y&i p50 noprint;
	BY year;
	VAR var_&y&i ;
	OUTPUT OUT = stat_&y&i P50(var_&y&i) = var_&y&i ;
RUN; 
%END;

*Insert more code that works fine;
%END
%MEND create_Table1;

*Create table with 10th percentile; %create_table1(y1,p10);

*Create table with 50th percentile;
%create_table1(y1,p50);

But when I try to mend my macro, I get an error:

 

  %ELSE %IF &statistic=p50 %THEN 
ERROR: There is no matching %IF statement for the %ELSE.
ERROR: A dummy macro will be compiled.
2739  %DO;

So, I'm wondering, have I messed up the formatting here, or is there potentially another

issue at large?

 

 

 

 

 

1 ACCEPTED SOLUTION

Accepted Solutions
Tom
Super User Tom
Super User

You cannot insert a statement between the %THEN clause and the %ELSE clause.

To the macro processor your comment is a statement. 

Personally I place the comments inside the macro code, not before them. Then they print in the log when the MPRINT option is on.

%IF &statistic=p10 %THEN  %DO;
*Table 1 Calculate 10th percentile if statistic = p10;
PROC MEANS DATA = table_&y&i p10 noprint;
	BY year;
	VAR var_&y&i ;
	OUTPUT OUT = stat_&y&i P10(var_&y&i) = var_&y&i ;
RUN; 
%END;

%ELSE %IF &statistic=p50 %THEN  %DO;
*Table 2 Calculate 50th percentile if statistic = p50;
...
%END;

You could also use either a block comment or a macro comment and it wouldn't count as a statement in between.  But then they won't print in the SAS log when MPRINT is on and the users of your macro will have a harder time understanding the log.

 

Types of comments:

* SAS comment ;
/* Block comment */
%* Macro comment ;

 

View solution in original post

4 REPLIES 4
Tom
Super User Tom
Super User

You cannot insert a statement between the %THEN clause and the %ELSE clause.

To the macro processor your comment is a statement. 

Personally I place the comments inside the macro code, not before them. Then they print in the log when the MPRINT option is on.

%IF &statistic=p10 %THEN  %DO;
*Table 1 Calculate 10th percentile if statistic = p10;
PROC MEANS DATA = table_&y&i p10 noprint;
	BY year;
	VAR var_&y&i ;
	OUTPUT OUT = stat_&y&i P10(var_&y&i) = var_&y&i ;
RUN; 
%END;

%ELSE %IF &statistic=p50 %THEN  %DO;
*Table 2 Calculate 50th percentile if statistic = p50;
...
%END;

You could also use either a block comment or a macro comment and it wouldn't count as a statement in between.  But then they won't print in the SAS log when MPRINT is on and the users of your macro will have a harder time understanding the log.

 

Types of comments:

* SAS comment ;
/* Block comment */
%* Macro comment ;

 

UniversitySas
Quartz | Level 8

Thanks, this solved it.

 

I would have never figured this out! 

ballardw
Super User

You may want to look into the AUTONAME option when creating output data sets.

 

Please examine (print or view the table) the results of running this code on a data set you should have available:

Proc means data=sashelp.class noprint;
   class sex;
   var height weight;
   output out=work.summary mean= max= min= std= / autoname;
run;

The autoname appends the statistic to the variable name (assuming the variable name + _ + statistic is 32 or fewer characters) so you might be able to reduce the calls to proc means/summary in a different fashion by calling either all the statistics or all the variables or both at one time.

 

If you really are only calling one statistic for one variable you can use <statistic>= ; with nothing else and the name of the output statistic is the variable name:

Proc means data=sashelp.class noprint;
   class sex;
   var weight;
   output out=work.summary skew= ;
run;
Tom
Super User Tom
Super User

Your macro as written doesn't need any branching.

 

Just use the value of the macro variable at the appropriate place in the code.

%MACRO create_Table(y,statistic);
%local i;
%DO i = 1 %TO 10;
* Use PROC MEANS to generate requested statistic ;
PROC MEANS DATA = table_&y&i &statistic noprint;
	BY year;
	VAR var_&y&i ;
	OUTPUT OUT = stat_&y&i &statistic(var_&y&i) = var_&y&i ;
RUN; 
*Insert more code that works fine;
%END
%MEND create_Table;

You can even get rid of the %DO loop.  Put all 10 of your VAR_&Y.1 to 10 variables into one input dataset and generate the statistic for all of them in one PROC into one output dataset. 

%MACRO create_Table(y,statistic);
* Use PROC MEANS to generate requested statistics ;
PROC MEANS DATA = table_&y &statistic noprint;
	BY year;
	VAR var_&y.1 - var_&y.10 ;
	OUTPUT OUT = stat_&y &statistic=;
RUN; 
*Insert more code that works fine;

%MEND create_Table;

sas-innovate-2024.png

Available on demand!

Missed SAS Innovate Las Vegas? Watch all the action for free! View the keynotes, general sessions and 22 breakouts on demand.

 

Register now!

What is Bayesian Analysis?

Learn the difference between classical and Bayesian statistical approaches and see a few PROC examples to perform Bayesian analysis in this video.

Find more tutorials on the SAS Users YouTube channel.

Click image to register for webinarClick image to register for webinar

Classroom Training Available!

Select SAS Training centers are offering in-person courses. View upcoming courses for:

View all other training opportunities.

Discussion stats
  • 4 replies
  • 417 views
  • 0 likes
  • 3 in conversation