BookmarkSubscribeRSS Feed
☑ This topic is solved. Need further help from the community? Please sign in and ask a new question.
PrinceAde
Obsidian | Level 7

Hi everyone, please I have confusion on how an indirect references works sas macro.
I don't understand how this resolves to type2;

%let value1 = dogs;
%let value2 = cats;
%let value3 = birds;

%let type1 = value1;
%let type2 = value2;
%let type3 = value3;

%let animal = type2;
%let final = animal;

%put &&&&&&final;

1 ACCEPTED SOLUTION

Accepted Solutions
Kurt_Bremser
Super User

3 iterations of resolution are done.

In the first, all double ampersandsvresolve to one ampersand, so you get

&&&final

In the second, the double ampersand becomes one, and &final resolves to animal, so you get

&animal

In the third, &animal resolves to

type2

which is what you get.

View solution in original post

8 REPLIES 8
PaigeMiller
Diamond | Level 26

If you run the macro debugging option

 

options symbolgen;

 

and then run your code again, you will see in the log:

 

 69         options symbolgen;
 70         %let value1 = dogs;
 71         %let value2 = cats;
 72         %let value3 = birds;
 73         
 74         %let type1 = value1;
 75         %let type2 = value2;
 76         %let type3 = value3;
 77         
 78         %let animal = type2;
 79         %let final = animal;
 80         
 81         %put &&&&&&final;
 SYMBOLGEN:  && resolves to &.
 SYMBOLGEN:  && resolves to &.
 SYMBOLGEN:  && resolves to &.
 SYMBOLGEN:  && resolves to &.
 SYMBOLGEN:  Macro variable FINAL resolves to animal
 SYMBOLGEN:  Macro variable ANIMAL resolves to type2
 type2
 82         

 

So double && resolves to & (repeatedly), then &FINAL resolves to animal, then &ANIMAL resolves to type2.

 

Better yet, avoid this use of &&&&&&& and find other ways to accomplish the task. I never use  more than a triple ampersand.

--
Paige Miller
Kurt_Bremser
Super User

3 iterations of resolution are done.

In the first, all double ampersandsvresolve to one ampersand, so you get

&&&final

In the second, the double ampersand becomes one, and &final resolves to animal, so you get

&animal

In the third, &animal resolves to

type2

which is what you get.

ballardw
Super User

Maybe running this will give you some clue:

%put &final;
%put &&final;
%put &&&final;
%put &&&&final;
%put &&&&&final;
%put &&&&&&final;
%put &&&&&&&final;
%put &&&&&&&&final;
%put &&&&&&&&&final;
%put &&&&&&&&&&final;
%put &&&&&&&&&&&final;
%put &&&&&&&&&&&&final;
%put &&&&&&&&&&&&&final;
%put &&&&&&&&&&&&&&final;
%put &&&&&&&&&&&&&&&final;

If you start writing code that requires more than && for indirect referencing be prepared to spend a lot of time debugging as the more indirect you try to do something the number of & required to get to "desired" result goes up quickly.

 

Note that multiple sets of indirect references have the same results.

Look at &&&Final. The first && resolve to & so you get & followed by &final. With &final=animal then you get &animal or  a result of type2.

 

2 to the nth power -1.

That's how many & for each level (n) of indirect referencing needed. You have lots of && resolving to & with more indirects.

 

I really hope this was an exercise as I would strongly recommend not trying to get that many indirect references to work consistently.

ChrisNZ
Tourmaline | Level 20

There should be few cases where you need more than 2 levels, but even for 2, I prefer a more explicit syntax:

%let value1 = dogs;
%let value2 = cats;
%let value3 = birds;

%let type1 = value1;
%let type2 = value2;
%let type3 = value3;

%let animal = type2;
%let final = animal;

%put 1.%superq(final);
%put 2.%superq(%superq(final));
%put 3.%superq(%superq(%superq(final)));
%put 4.%superq(%superq(%superq(%superq(final))));
1.animal
2.type2
3.value2
4.cats

Kurt_Bremser
Super User

Just to give you some perspective: in more than two decades of professional work with SAS, and more than a decade as data warehouse administrator and chief developer, being responsible for 1000+ SAS jobs running in production, I never had to use an indirect macro variable reference. Not once.

I encountered this technique here for the first time.

So don't waste too many precious brain cycles on this. There's much more important SAS stuff to learn.

ChrisNZ
Tourmaline | Level 20

@Kurt_Bremser 

I've seen the construct &&&var&i used on regularly. I'm surprised you haven't.

 

Kurt_Bremser
Super User

Probably because I always keep data in datasets, which reduces the need for macro arrays.

Anyway, just deciphering a mass of ampersands takes much too much time when maintaining programs, that's why it's so impractical.

yabwon
Onyx | Level 15

I think the macroArray package can make work with macro variable arrays (i.e. &&prefix&sufix constructs) easier.

 

Article describing it: https://www.lexjansen.com/pharmasug/2024/AP/PharmaSUG-2024-AP-108.pdf has been published in PharmaSUG 2024 proceedings  and re-published in WUSS 2024 proceedings.

 

The package itself is located here: https://github.com/SASPAC/macroarray

 

All the best

Bart

_______________
Polish SAS Users Group: www.polsug.com and communities.sas.com/polsug

"SAS Packages: the way to share" at SGF2020 Proceedings (the latest version), GitHub Repository, and YouTube Video.
Hands-on-Workshop: "Share your code with SAS Packages"
"My First SAS Package: A How-To" at SGF2021 Proceedings

SAS Ballot Ideas: one: SPF in SAS, two, and three
SAS Documentation



SAS Innovate 2025: Save the Date

 SAS Innovate 2025 is scheduled for May 6-9 in Orlando, FL. Sign up to be first to learn about the agenda and registration!

Save the date!

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.

SAS Training: Just a Click Away

 Ready to level-up your skills? Choose your own adventure.

Browse our catalog!

Discussion stats
  • 8 replies
  • 701 views
  • 3 likes
  • 6 in conversation