Reputation: 15
So I've been attempting to write a SAS macro which evaluates whether or not a string has a certain substring in a given variable.
%let variable = "file_name.zip";
%let zip_flag = %sysfunc(find(&variable., ".zip", i));
%put &zip_flag.;
Unfortunately, the zip_flag
macro variable always returns "0". I have attempted to change the flag within the find statement to be within quotes (this throws a different error), I have removed the period from the substring quote, call dequote
on the call to &variable.
, and have tried to change this statement to use prxmatch
instead. All of these changes were either ineffective or caused other errors.
Upvotes: 0
Views: 1456
Reputation: 51611
The macro variable VARIABLE has the string .zip"
in it, but not the string ".zip"
that your function call is looking for.
When you include quote characters in a macro variable they are part of the value. Remember that everything is text to the macro processor. The macro triggers &
and %
let it know when to treat the text as something special. So you don't have to quote string literals like you would in a programming language since it will not get confused and think that zip
is the name of a variable.
For the %SYSFUNC() macro function to pass the strings onto the data step function it needs to convert the text it has into the appropriate variable type for that parameter to the data step function. It has a lot of trouble with functions that have flexible syntax where some parameters are allowed to be either character values or numeric values. So %SYSFUNC() tries to guess which data type your text represents.
In this case the modifier and start position parameters to FIND() can be in either order so %SYSFUNC() does not know which you mean. So it checks whether the text could be a number.
If you have included the letter I in the setting used with the MISSING statement then the single letter I will be interpreted as the numeric missing value .I
and so a number instead of character string.
293 %let variable = "file_name.zip";
294 %let zip_flag = %sysfunc(find(&variable.,.zip,i));
295 %put &=zip_flag;
ZIP_FLAG=.
You can avoid that extra confusion by including another modifier. You could even just include I twice.
316 %let variable = "file_name.zip";
317 %let zip_flag = %sysfunc(find(&variable.,.zip,ii));
318 %put &=zip_flag;
ZIP_FLAG=11
Upvotes: 2