Using SAS EG 7.1.
How do I resolve the below? THank you
ERROR: A character operand was found in the %EVAL function or %IF condition where a numeric operand is required. The condition was:
A AND B
CODE:
%DO YEAR=&FIRSTYR %TO &LASTYR;
%do i = 1 %to %sysfunc(countw(&monlist.));
%let month = %sysfunc(putn(%scan(&monlist.,&i.),z2.)); /*i is numeric; whereas &MONTH is char (01,02,etc). So convert numeric i to char &MONTH.*/
PROC SORT DATA =CN; BY ID Date; RUN;
PROC SORT DATA = Tax&YEAR.&MONTH; BY ID Date ; RUN;
DATA TaxCN&YEAR.&MONTH;
MERGE Tax&YEAR.&MONTH(IN=A) CN(IN=B);
BY ID Date;
%IF A AND B %THEN MERGEID='1';%ELSE
%IF A AND NOT B %THEN MERGEID='2';%ELSE
%DO; MERGEID='4';%END;
RUN;
DATA FA&YEAR.&MONTH_CN (drop=MERGEID);
set FA&YEAR.&MONTH_CN;
IF MERGEID='2' Or MERGEID='1';
RUN;
PROC SORT DATA =FACN&YEAR.&MONTH; BY UIN; RUN;
%END;
%END;
Macro language is used to dynamically create program text; it is dealt with long before a data step is executed.
Also, macro language ONLY knows the datatype character, but not numeric. Special functions need to be used for numeric operations, when necessary.
In your case,
%IF A AND B %THEN MERGEID='1';%ELSE
%IF A AND NOT B %THEN MERGEID='2';%ELSE
%DO; MERGEID='4';%END;
means that the macro engine, when it encounters the "and" operator, needs boolean values, but the texts "A" and "B" are not numbers. The numeric variables A and B will exist much later (during data step execution), when the macro has long before finished. The macro cannot know them.
If I read your intentions right, you just need to use the correct data step language at this point:
if A and B
then MERGEID = '1';
else if A and not B
then MERGEID = '2';
else MERGEID = '4';
Macro language is used to dynamically create program text; it is dealt with long before a data step is executed.
Also, macro language ONLY knows the datatype character, but not numeric. Special functions need to be used for numeric operations, when necessary.
In your case,
%IF A AND B %THEN MERGEID='1';%ELSE
%IF A AND NOT B %THEN MERGEID='2';%ELSE
%DO; MERGEID='4';%END;
means that the macro engine, when it encounters the "and" operator, needs boolean values, but the texts "A" and "B" are not numbers. The numeric variables A and B will exist much later (during data step execution), when the macro has long before finished. The macro cannot know them.
If I read your intentions right, you just need to use the correct data step language at this point:
if A and B
then MERGEID = '1';
else if A and not B
then MERGEID = '2';
else MERGEID = '4';
Try converting the "i" value into Char by removing trailing blanks. I think that should be the issue and give a try something like below
%do i = 1 %to %sysfunc(trim(left(put((countw(&monlist.)),best.));
A far simpler methodology, and one which should be on the first page of every learning manual, is data structure. You are finding that your life is difficult because of one simple fact, you have put "data" into an area which is not designed to hold "data". Dataset names, column names, these are here for the purpose of making programming simpler and more efficient, they are Not designed to hold "data". Column labels, and observations are designed to hold data.
The reason I point this out is that by a simple structure change to your data, you can eliminate all that code, and write simple basic efficient and easy to maintain Base SAS code, which will do exactly the same purpose. Where you have datasets called taxYYYYMM, create one dataset, which has all the data, with columns for YYYY and MM:
data tax201502; a=1; output; run; data tax201503; a=2; output; run; data tax; set work.tax: indsname=nme; year=input(substr(scan(nme,2,"."),4,4),4.); month=input(substr(scan(nme,2,"."),8,2),2.); run;
Now you have one dataset with all your data in one place. You can manipulate this one dataset using simple basic datasteps, no need for looping or macros or any other complicated code. And if for some reason you need to split them up again later on, then that again is a simple datastep output routine. Remember the data structure is there for your benefit.
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 16. 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.
Select SAS Training centers are offering in-person courses. View upcoming courses for: