DATA Step, Macro, Functions and more

Calling a macro with return value inside datastep

Accepted Solution Solved
Reply
Occasional Contributor
Posts: 9
Accepted Solution

Calling a macro with return value inside datastep

Folks, I have a problem regarding calling a macro from data step. This data step is inside another macro. But fundamentally , it is not possible to get macro value in ‘data step’, although some alternate like ‘call execute’ can be used. But I am not able to get it done. I have below code which is not working and making data variable set empty instead of returning value. Is there any alternative to achieve so ? %Macro Set_nestedval2(TaskID,Status,Section,DSNameP,DSVarP,DSVarP1); /*%let location_1=%location('Train'); */ Data &DSNameP; Set &DSNameP ; &DSVarP=call execute('%nrstr(%location(type=Train));'); /* &DSVarP=& location; */ Run; %put &location_1; %mend; %macro location(type,location=); %if &type='Airplane' %then %let location=Airport; %if &type='Train' %then %let location=Railway_Station; /*%put type is &type.; */ &location; /* this line is effectively the "return value" */ %mend location; %Set_nestedval2(1,2,3,’DM’,’Entity_name’,’’); Thanks,

Accepted Solutions
Solution
2 weeks ago
Super User
Posts: 5,085

Re: Calling a macro with return value inside datastep

You got a lot of the pieces right.  First, the small piece:  you do have an extra semicolon here:

 

&location;

 

The %LOCATION macro should return &location without a semicolon.

 

Second, it's not clear what value you want to assign in your DATA step.  Do you want:

 

&DSVarP = Railway_Station;

&DSVarP = "Railway_Station";

 

Using the version with the quotes, you would simply use:

 

&DSVarP = "%location('Train')";

 

Remove the double quotes if you don't need them.

View solution in original post


All Replies
Super User
Posts: 6,947

Re: Calling a macro with return value inside datastep

First of all, use proper code formatting and a code window ({i} or "little running man" button) for posting code. This spaghetti-code is an eyesore.

 

You can't insert code from a dynamically called macro back into the datastep. The datastep is compiled and cannot be changed once it starts running.

 

What is the purpose of this honorable mention for the Obfuscated SAS Code Contest?

---------------------------------------------------------------------------------------------
Maxims of Maximally Efficient SAS Programmers
Super User
Super User
Posts: 7,407

Re: Calling a macro with return value inside datastep

What is it your trying to achieve?  Follow the guidance by the post button:

Post example test data, in the form of a datastep, using the code window - its the {i}.

Post what you want out at the end.

Post any logs or logic which may help explain.  

 

After parsing the unformatted text you provide below, I don't see the point in any of the code.  Why not just format the given variable and avoid all this unecessary obfuscation?  I.e. have a format type where Airplane=Airport,... and then put type into a new variable with that format.

 

To demonstrate the code window (again the {i} above the post are):

%Macro Set_nestedval2(TaskID,Status,Section,DSNameP,DSVarP,DSVarP1); 
/*%let location_1=%location('Train'); */ 
  Data &DSNameP; 
    Set &DSNameP ; 
    &DSVarP=call execute('%nrstr(%location(type=Train));'); 
    /* &DSVarP=& location; */ 
  Run; 
  %put &location_1; 
%mend; 

%macro location(type,location=); 
  %if &type='Airplane' %then %let location=Airport; 
  %if &type='Train' %then %let location=Railway_Station; 
  /*%put type is &type.; */ &location; /* this line is effectively the "return value" */ 
%mend location; 
%Set_nestedval2(1,2,3,’DM’,’Entity_name’,’’);;
Occasional Contributor
Posts: 9

Re: Calling a macro with return value inside datastep

[ Edited ]

Hello All,

 

Reposting the simple modified code.

 

Here what I want is that datastep in first macro named 'Set_nestedval2' must be able to fetch the value returning from second macro ‘location’. And this location returned must be set as value in one of the column of above ‘dm’.

 

Would like to mention that without outside datastep, I am able to get the returning value.

 

%Macro Set_nestedval2(TaskID,Status,Section,DSNameP,DSVarP,DSVarP1); 
Data dm; &DSVarP=call execute('%nrstr(%location(type=Train));'); Run; %mend;
****** Macro 2 ******* %macro location(type,location=); %if &type='Airplane' %then %let location=Airport; %if &type='Train' %then %let location=Railway_Station; &location; %mend location;

********* calling parent macro ************ %Set_nestedval2(1,2,3,’DM’,’Entity_name’,’’);

 

Super User
Super User
Posts: 7,407

Re: Calling a macro with return value inside datastep

As I mentioned above, there is no value in this code.  All you are doing is fighting the software when a simple format will do.

 

%Macro Set_nestedval2(TaskID,Status,Section,DSNameP,DSVarP,DSVarP1); 
  Data dm;
    &DSVarP="%location(type=Train)";  
  Run; 
%mend; 

%macro location(type,location=); 
  %if &type.=Airplane %then %let location=Airport; 
  %if &type.=Train %then %let location=Railway_Station; 
  &location. 
%mend location; 

options mprint symbolgen mlogic;
%Set_nestedval2(1,2,3,DM,Entity_name,);

It works, but I really advise against it.

Solution
2 weeks ago
Super User
Posts: 5,085

Re: Calling a macro with return value inside datastep

You got a lot of the pieces right.  First, the small piece:  you do have an extra semicolon here:

 

&location;

 

The %LOCATION macro should return &location without a semicolon.

 

Second, it's not clear what value you want to assign in your DATA step.  Do you want:

 

&DSVarP = Railway_Station;

&DSVarP = "Railway_Station";

 

Using the version with the quotes, you would simply use:

 

&DSVarP = "%location('Train')";

 

Remove the double quotes if you don't need them.

Occasional Contributor
Posts: 9

Re: Calling a macro with return value inside datastep

[ Edited ]

&DSVarP= "%location('Train')"

 

Above is the solution. Adding double quotes give me the result.

☑ This topic is SOLVED.

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

Discussion stats
  • 6 replies
  • 118 views
  • 4 likes
  • 4 in conversation