DATA Step, Macro, Functions and more

how to take a list of n variables and assign them to macro variables cvar_1...cvar_n??

Accepted Solution Solved
Reply
Contributor
Posts: 42
Accepted Solution

how to take a list of n variables and assign them to macro variables cvar_1...cvar_n??

I know how to assign a straight list of macro variables to one macro variable each, but how do you do it so each value in the list is it's own macro variable as such:

each variable in the list will be of varying lengths and the list will be any number of variables up to N.

%let macrolist= var1 var2 var3 var4......varN;

Ultimately I want to get to this point, where cvar1, cvar2, cvar3....cvarN are the variables from the list above.

%do i=1 %to N;

call symput ('cvar'||(&i), var&i);


Accepted Solutions
Solution
‎07-18-2011 07:27 PM
Super User
Super User
Posts: 7,074

how to take a list of n variables and assign them to macro variables cvar_1...cvar_n??

You seem to be saying that you want to split the list of words in &MACROLIST into separate variables.  Do you want just the text string? or the value of the macro variable that has that name?

Lets do both and call the resulting macro variables CVAR... and CVAL.... (for variable and value).

If we assume that you know the value of N then you can do:

%do i=1 to &n ;

   %let cvar&i = %scan(&macrolist,&i,%str( ));

   %let cval&i = &&&cvar&i ;

%end;

If you do not know the value of N then you will need to increment the counter variable (I in the code above) manually using %let i=%eval(&i + 1) and test for and empty result from the %scan() function call to terminate the loop.

If you want to be able to reference the new macro variables after the currently running macro finishes you might want to add a %global statement inside the %do loop.

NOTE: CALL SYMPUT is for use in regular SAS. You should be able to manipulate you macro variables with just macro logic and statements.

View solution in original post


All Replies
PROC Star
Posts: 7,487

how to take a list of n variables and assign them to macro variables cvar_1...cvar_n??

Not sure if I correctly understand what you are asking.  You can create a macro variable using proc sql.  Thus you could use something like (untested):

proc sql noprint;

  select name into : wantlist

     separated by " "

       from dictionary.columns

          where libname="THELIBYOUWANT" and

           memname="THEFILEYOUWANT";

quit;

You can also incorporate a keep statement to limit which variables you want to include.

HTH,

Art

Contributor
Posts: 42

how to take a list of n variables and assign them to macro variables cvar_1...cvar_n??

Thanks for the reply Art.  If I understand you correctly, you are suggesting putting all the macro variables into 1 new macro variable, I'm talking about taking the list and separating each variable from 1.....to N and creating a new macro variable for each individual one, so that if there are 10 vars in the list, then there will be 10 macro variables.  I hope that makes sense.

PROC Star
Posts: 7,487

how to take a list of n variables and assign them to macro variables cvar_1...cvar_n??

Take a look at: http://www.nesug.org/proceedings/nesug08/cc/cc08.pdf

I think that describes what you are looking for

Solution
‎07-18-2011 07:27 PM
Super User
Super User
Posts: 7,074

how to take a list of n variables and assign them to macro variables cvar_1...cvar_n??

You seem to be saying that you want to split the list of words in &MACROLIST into separate variables.  Do you want just the text string? or the value of the macro variable that has that name?

Lets do both and call the resulting macro variables CVAR... and CVAL.... (for variable and value).

If we assume that you know the value of N then you can do:

%do i=1 to &n ;

   %let cvar&i = %scan(&macrolist,&i,%str( ));

   %let cval&i = &&&cvar&i ;

%end;

If you do not know the value of N then you will need to increment the counter variable (I in the code above) manually using %let i=%eval(&i + 1) and test for and empty result from the %scan() function call to terminate the loop.

If you want to be able to reference the new macro variables after the currently running macro finishes you might want to add a %global statement inside the %do loop.

NOTE: CALL SYMPUT is for use in regular SAS. You should be able to manipulate you macro variables with just macro logic and statements.

Contributor
Posts: 42

how to take a list of n variables and assign them to macro variables cvar_1...cvar_n??

Thanks Tom,

Yes, I'm trying to just capture the text string with each word broken apart from the original list. 

I've tried the following code and can't get this to work quite right...  Am I doing something wrong?  The value of &cvar1 should be "house".

%let macrolist = house garage car speaker;

%let n=4;

%macro assign;

     %do i=1 %to &n;

     %global;

          %let cvar&i=%scan(&macrolist,1,%str());

      %end;

%mend assign;

%assign;

%put cvar1;

Valued Guide
Posts: 2,177

how to take a list of n variables and assign them to macro variables cvar_1...cvar_n??

replace the 1 with &i in the %scan

insert a blank within the brackets of %str()

define which var to global, fully like:

%global cvar&i ;

learn to develop macros with

option symbolgen ;

Contributor
Posts: 42

how to take a list of n variables and assign them to macro variables cvar_1...cvar_n??

Thank you Peter, that did the trick.  The 1 was an error on my part of typing as I did have the &i in the original.  I'm familiar with the symbolgen mprint mlogic as well, thank you. 

My question is I was able to run this not using the %str(' ') inside with the blank quotes and just using the empty single quotes alone ' '.  What is the purpose of the %str in this case?  I'm not familiar with the %str and thus was curious what it does here. 

thank you all for your help.

Super User
Super User
Posts: 7,074

how to take a list of n variables and assign them to macro variables cvar_1...cvar_n??

The %str( ) is useful to prevent the macro processor from ignoring the space. When you use single quotes or double quotes around characters they actually become part of the string.

This means that %scan(&myvar,&i,%str( )) means something different than %scan(&myvar,&i,' ').

The first only uses blanks as the delimiter when scanning.  The second one will use either blanks or single quote characters.

Contributor
Posts: 42

how to take a list of n variables and assign them to macro variables cvar_1...cvar_n??

Thanks for the response Tom, makes sense. 

Contributor
Posts: 42

how to take a list of n variables and assign them to macro variables cvar_1...cvar_n??

Tom,

Regarding how to do this when N is unknown, I'm not sure how to do it with your recommendations above.  I've tried it several ways using a %do %while and %do %until and trying to determine if the value is blank to terminate the loop, but I keep getting errors.  Can you show me how I would do this if the N is unknown?

thanks again!

Super User
Super User
Posts: 7,074

how to take a list of n variables and assign them to macro variables cvar_1...cvar_n??

As long as you are using SAS verison 9 you should be able to use the COUNTW function.

%let n=%sysfunc(countw(&macrolist));

Otherwise you can loop and increment your own counter.  You can either test for empty using something like:

%if (&var = ) %then ....

Or test for zero length

%if %length(&var)=0 %then ...

They test slightly different things, but for this problem they are equivalent as you are using blanks for your delimiter.

Here is one way to count. Remember to subtract one because it stops on an empty word.

%let n=1 ;

%do %while(%scan(&macrolist),&n) ne ) ;

    %let n=%eval(&n + 1);

%end;

%let n=%eval(&n -1 );

Contributor
Posts: 42

how to take a list of n variables and assign them to macro variables cvar_1...cvar_n??

Thanks again Tom!  Excellent solutions for sure!  The first one worked perfect just using the countw function which I was unaware of.

I tried the count one as well and that did the trick too.

Really appreciate it!

🔒 This topic is solved and locked.

Need further help from the community? Please ask a new question.

Discussion stats
  • 12 replies
  • 259 views
  • 6 likes
  • 4 in conversation