BookmarkSubscribeRSS Feed
Aman4SAS
Obsidian | Level 7

Hi team, 

we need help in sas macro

 if we can use below 

data test;
do i = 2, 5, 7 ;
x=i;
output;
end;
run;

 

so what we can not use 

 

%macro x();

%do i=3,6,8;

statements;

%end;

%mend;

%x;

12 REPLIES 12
Aman4SAS
Obsidian | Level 7

I apology if i did mistake.

 

But i need to run my programe for selective day. and i want to run my do loop for that.

but i am getting error that u r missing %to. So is there any possibility that i can use %do with out using %to.???

RW9
Diamond | Level 26 RW9
Diamond | Level 26

As @Kurt_Bremser has mentioned, Macro language is only present to generate text, it does not do any processing.  Therefore constructs used in Base SAS which is the programming language do not always carry through to Macro.  Do list of values is one of these constructs.  

I believe we have been over this several times before.  Do data processing in Base SAS, that is what it is for.  What is it your trying to do with this code?

Aman4SAS
Obsidian | Level 7

i want to pick selective data by using :

 

%macro x();

%do i = 3 ,6, 7,9;

proc report data= Ivalue_&i;

run;

%end;

%mend;

Kurt_Bremser
Super User
data control;
input i;
cards;
3
6
7
9
;
run;

%macro x(i);
proc report data= Ivalue_&i;
run;
%mend;

data _null_;
set control;
call execute('%x(' !! strip(put(i,best.)) !! ') ');
run;
Kurt_Bremser
Super User

Post the code you want to run for a series of days, showing how the days are represented in the code as is (for a single run), and from where you will get the days for the dynamic execution (dataset?).

 

When writing repeatable code, follow this sequence:

- write code for one iteration

- identify variable parts

- replace with macro values

- create a means to supply these values (macro %do loop, datastep with call execute, ...) repeatedly

 

Tom
Super User Tom
Super User

The %DO command does not have all of the functionality of the DO command.

To process a list I usually put the list into a macro variable and use %SCAN() to pull the individual items.

%macro x(list);
%local i value ;
%do i=1 %to %sysfunc(countw(&list));
  %let value = %scan(&list,&i);
   statements using &value ;
%end;
%mend;
%x(2 5 7);
Aman4SAS
Obsidian | Level 7

Thanks for ur answer.

 

i have done same as alternate option.

%let list=13|14|15|25|26|27;
%do part = 1 %to 6;
%let i=%scan(&list,&part,%str(|));
%put &i;
%end;

 

but for future prospect i want study this more. bcaz i have tried "in" with %do same also does not work. is there any document so i can study more for the same.

 

Thanks in advance for all of ur advice.

Tom
Super User Tom
Super User

Note there is no need to use %STR() around | as it is not a macro trigger. That is one good reason to use it as the delimiter in a list of values.  Personally I much prefer to use spaces as delimiters since it is much easier to type and read, but that can be a problem if the values can contain spaces.  If your values can contain other default delimiters for %SCAN() then you do need to use the third argument to %SCAN() to let it know what specific delimiter(s) to use.  There is also a fourth argument to %SCAN() that can be used to add modifiers to control how it parses the string.

 

The IN operator is just a method for testing if a value appears in a list a values. Not sure what it would have to do with a DO loop.  

 

Note that there are limitations on using the IN operator within macro code since it was not originally recognized as a keyword by the macro processor.  There are system options and options on the %MACRO statement to control whether and how the IN operator works in macro code.

 

The SAS documentation is on-line at sas.com.  I usually just GOOGLE until I find the right document and then look around.

Cynthia_sas
SAS Super FREQ
And, in addition to all of these excellent suggestions, here's an overview of Macro processing and how it works to get you started reading about why you don't confuse DO processing with %DO processing:
https://support.sas.com/resources/papers/proceedings13/120-2013.pdf
cynthia
slchen
Lapis Lazuli | Level 10

 If you do want to use %do loop, you could try this: 

 

option minoperator mindelimiter='|';

%macro test;
%let list=13|14|15|25|26|27;
%do part = 1 %to 30;
%if &part in &list %then
%put ∂
%end;
%mend;

%test;

ChrisNZ
Tourmaline | Level 20

@slchen It's a good habit to declare your variables as local. You'll save yourself many headaches.

So this is a (slightly) better macro:


%macro test/minoperator mindelimiter='|';
  %local list part;
  %let list=13|14|15|25|26|27;
  %do part = 1 %to 30;
    %if &part in &list %then %put &=part;
  %end;
%mend;

%test;


sas-innovate-2024.png

Join us for SAS Innovate April 16-19 at the Aria in Las Vegas. Bring the team and save big with our group pricing for a limited time only.

Pre-conference courses and tutorials are filling up fast and are always a sellout. Register today to reserve your seat.

 

Register now!

How to Concatenate Values

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.

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
  • 12 replies
  • 2673 views
  • 8 likes
  • 7 in conversation