Hi All,
I'm trying to quote (mask) some % and & that appear in labels, using SGPLOT. I tried the usual %NRSTR, and then even single quotes, but neither worked.
So now I'm thinking the issue is that SGPLOT writes out a graphics template in the background (?) , and the value of the label gets unquoted when that happens.
Any way to stop that unquoting? (current kludge is to just insert a space after % &, so that they don't look like macro triggers.)
Thanks,
--Q.
14 proc sgplot data=sashelp.class; 15 scatter x=height y=weight; 16 xaxis label='%text1 &text2'; 17 yaxis label="%nrstr(%%text3 &text4)"; 18 run; WARNING: Apparent invocation of macro TEXT1 not resolved. WARNING: Apparent symbolic reference TEXT2 not resolved. WARNING: Apparent invocation of macro TEXT3 not resolved. WARNING: Apparent symbolic reference TEXT4 not resolved.
With no macro quoting, get warnings twice (once for xaxis statement and once for use of the template to write the graph, perhaps).
14 proc sgplot data=sashelp.class; 15 scatter x=height y=weight; 16 xaxis label="%text1 &text2"; WARNING: Apparent invocation of macro TEXT1 not resolved. WARNING: Apparent symbolic reference TEXT2 not resolved. 17 run; WARNING: Apparent invocation of macro TEXT1 not resolved. WARNING: Apparent symbolic reference TEXT2 not resolved.
Quentin, how about this?
%let text1 = %NRSTR(%%things);
%let text3 = %NRSTR(some label &beautiful words);
proc sgplot data=sashelp.class;
scatter x=height y=weight;
xaxis label = '&text1.';
yaxis label= '&text3.';
run;
It seems that is doing what you want?
Hi.
Is this closer to what you want?
%let text1 = "% of things ";
%let text2 = " some label & beautiful words";
proc sgplot data=sashelp.class;
scatter x=height y=weight;
xaxis label = &text1.;
yaxis label= &text2.;
run;
Why do you have a macro call for %text1? what is the macro for?
Hi Anca,
Your example doesn't cause warnings because you have a space after the % and & signs.
%text1 is not a macro call, it's intended to be just text, so I added macro quoting and single quotes, but they are becoming unquoted and causing the warning message.
Maybe a clearer example would be:
xaxis label= '%Bias' ;
Goal is to have a label that says %Bias, without SAS trying to execute a macro named %Bias. Current workaround is to just add a space, so:
xaxis label= '% Bias'; /*space after % sign so that it's not a macro trigger*/
Thanks,
--Q.
Hey Quentin,
First of all, to prevent % and & from being resolved in a string in SAS, you should use single quotes (') instead of double quotes ("). With that said, there was still an issue with the SG procedures that caused the warnings to generate. This issue was addressed in SAS 9.4. You should still be able to get the correct output, though.
Thanks!
Dan
I see, thank you for clarifying. So, you end up with the result you want, right? but you'd just like to avoid the warnings - good practice to have a warning free code
I am curious how to fix it...?
Quentin, how about this?
%let text1 = %NRSTR(%%things);
%let text3 = %NRSTR(some label &beautiful words);
proc sgplot data=sashelp.class;
scatter x=height y=weight;
xaxis label = '&text1.';
yaxis label= '&text3.';
run;
It seems that is doing what you want?
Nifty, thanks Anca!
So if my theory is correct about what is happpening (values becoming unquoted when the template is written), then you have avoided the problem by quoting twice.
The single quotes prevent the text from being resolved when the template is being written.
Then the template gets written with %nrstr() there as part of the value of the label. So %nrstr() does its work when the template is used.
proc sgplot data=sashelp.class; scatter x=height y=weight; xaxis label ='%nrstr(%%things)'; /*%nrstr() inside of single quotes, due to sgplot macro unquoting oddity, fixed in 9.4*/ yaxis label= '%nrstr(some label &beautiful words)'; run;
Thanks Dan for confirming this is a known issue of SG procs resolving quoted macro references. Will look forward to 9.4.
--Q.
I realized since you can have SGPLOT output the template code, I could test my theory of what was happening in background. Here are 3 examples with different attempts at quoting (Anca's successful double-quoting, followed by two approaches that "should" work according to the macro quoting "rules":
proc sgplot data=sashelp.class tmplout="d:\junk\tmpl_1.sas"; scatter x=height y=weight; xaxis label ='%nrstr(%%things)'; yaxis label= '%nrstr(some label &beautiful words)'; run; proc sgplot data=sashelp.class tmplout="d:\junk\tmpl_2.sas"; scatter x=height y=weight; xaxis label ="%nrstr(%%things)"; yaxis label= "%nrstr(some label &beautiful words)"; run; proc sgplot data=sashelp.class tmplout="d:\junk\tmpl_3.sas"; scatter x=height y=weight; xaxis label ='%things'; yaxis label= 'some label &beautiful words'; run;
When I look at the template, Anca's double quoting produces:
proc template; define statgraph sgplot; begingraph /; layout overlay / xaxisopts=( Label="%nrstr(%things)" type=linear ) yaxisopts=( Label="%nrstr(some label &beautiful words)" type=linear ); ScatterPlot X=Height Y=Weight / primary=true LegendLabel="Weight" NAME="SCATTER"; endlayout; endgraph; end; run;
Only surprise for me above is that the double %% from label='%nrstr(%%things)' is gone.
But both of the other versions both write the unqouted:
proc template; define statgraph sgplot; begingraph /; layout overlay / xaxisopts=( Label="%things" type=linear ) yaxisopts=( Label="some label &beautiful words" type=linear ); ScatterPlot X=Height Y=Weight / primary=true LegendLabel="Weight" NAME="SCATTER"; endlayout; endgraph; end; run;
Quite interesting behavior - way above my head to pretend I could explain any of it.
I am glad it is fixed in 9.4
Cheers!
A little bit late ( summary of direct exchanges with Quentin)
Sgplot has hidden GTL code you are able to change after captur by a tmpout= option..
So there is a way to use a modified template issued from the original one
and then make substitution of text through template macro variable or
ordinary macro variable substitution
Andre
an example:
libname tpl "d:\My SAS Files\tpl";
ods path tpl.sgd(update) sasuser.templat(read) sashelp.tmplmst(read);
proc template;
define statgraph tpl.sgplotquentin;
dynamic _text1 _text2;
begingraph /;
layout overlay / xaxisopts=( Label=_text1 type=linear ) yaxisopts=( Label=_text2 type=linear ); ScatterPlot X=Height Y=Weight / primary=true LegendLabel="Weight" NAME="SCATTER";
endlayout;
endgraph;
end; run;
%let val=2;
%let _text1=A & Co&val.;
%macro render;
proc sgrender data=sashelp.class template=tpl.sgplotquentin;
dynamic _text1=" &_text1. "
_text2='Growing %company';
run;
%mend;
%render
SAS Innovate 2025 is scheduled for May 6-9 in Orlando, FL. Sign up to be first to learn about the agenda and registration!
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.
Ready to level-up your skills? Choose your own adventure.