Hi. I need some help resolving an error in my program. I've provided the full program code below so that you can see it in action yourself.
In my program I build a macro variable that contains a list of rules seperated by # signs. In the program below the macro variable value looks like this:
A.ACTUAL_DLVRY_DATE IS NULL AND B.ACTUAL_DLVRY_DATE IS NOT NULL#A.ACTUAL_DLVRY_DATE > B.ACTUAL_DLVRY_DATE
Then I can use the %scan function to pull individual rules from the list.
the_rule=%scan(&rule_list, 1,#);
the_rule=%scan(&rule_list, 2,#);
These statements pull the rule values accordingly to the increment value:
A.ACTUAL_DLVRY_DATE IS NULL AND B.ACTUAL_DLVRY_DATE IS NOT NULL
A.ACTUAL_DLVRY_DATE > B.ACTUAL_DLVRY_DATE
But when I attempt to alter this statement to make it more dynamic using _N_ it errors out. See the error below. I'm doing this so that _n_ automatically increments for each record in my dataset.
the_rule=%scan(&rule_list, _n_,#);
The error looks like the following:
2201 data _null_;
2202 set QueryRules end=eof;
2203 by Rule_Order;
2204 file '/home/ssbuechl/input_whens.sas';
2205 the_rule=%scan(&rule_list, _n_,#);
-
22
ERROR: A character operand was found in the %EVAL function or %IF condition where a numeric operand is required. The condition
was: _n_
ERROR: Argument 2 to macro function %SCAN is not a number.
ERROR 22-322: Syntax error, expecting one of the following: a name, a quoted string, a numeric constant, a datetime constant,
a missing value, INPUT, PUT.
2206 put THE RULE: the_rule;
2207 run;
NOTE: The SAS System stopped processing this step because of errors.
Here's the complete program you can run yourself...
rsubmit;
data QueryRules;
infile cards dsd dlm='|' truncover ;
informat analysis_desc $34. rule $64.;
input analysis_desc $ rule $ rule_order;
cards;
ACTUAL DELIVERY DATE MISSING IN IV|A.ACTUAL_DLVRY_DATE IS NULL AND B.ACTUAL_DLVRY_DATE IS NOT NULL|1
ACTUAL DELIVERY DATE LATER IN IV|A.ACTUAL_DLVRY_DATE > B.ACTUAL_DLVRY_DATE|1.5
run;
proc print; run;
* Sort prep for call to BuildQueryData macro below ;
proc sort data=QueryRules;
by rule_order;
run;
proc sql;
select trim(rule) into : rule_list separated by '#' from QueryRules;
quit;
%PUT CHECK: RULE_LIST: &RULE_LIST;
data _null_;
set QueryRules end=eof;
by Rule_Order;
file '/home/ssbuechl/input_whens.sas';
the_rule=%scan(&rule_list, _n_,#);
put THE RULE: the_rule;
run;
endrsubmit;
DATA steps do not use macro functions to process the data. With a couple of changes, you could use SCAN instead of %SCAN:
the_rule = scan("&rule_list", _n_, '#');
Data steps require text strings to be surrounded by quotes (macro language does not). Be sure to use double quotes the first time, but either single or double quotes around # would work.
Macro function? Which one?
DATA steps do not use macro functions to process the data. With a couple of changes, you could use SCAN instead of %SCAN:
the_rule = scan("&rule_list", _n_, '#');
Data steps require text strings to be surrounded by quotes (macro language does not). Be sure to use double quotes the first time, but either single or double quotes around # would work.
Here's an idea.
Show us the actual values you are building from ( the data set you use to make this complex variable and processing problem), a small set would do, AND the desired SAS code you want that data set to create.
You have asked multiple questions with this same data, bad mixing of MACRO code inside DATASTEP and have never provided what the actual final output for a small set of it should actually look like.
I really believe that you have added lots of headaches by picking an approach (combining those values) when a more direct result would be possible without it.
Are you ready for the spotlight? We're accepting content ideas for SAS Innovate 2025 to be held May 6-9 in Orlando, FL. The call is open until September 25. Read more here about why you should contribute and what is in it for you!
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.