This seems to work for me.
data test;
input HOSPSTCO $ ;
cards;
23000
33000
02124
34002
55343
;
run;
proc format;
invalue $ FIPS
'23', '33', '50', '25', '44', '09' = 1
'36', '42', '34' = 2
'55', '26', '17', '18', '39' = 3
'29', '38', '46', '31', '20', '27', '19' = 4
'10', '24', '11', '51', '54', '37', '45', '13', '12' = 5
'21', '47', '28', '01' = 6
'40', '48', '05', '22' = 7
'16', '30', '56', '32', '49', '08', '04', '35' = 8
'02', '53', '41', '06', '15' = 9
;
run;
data test2;
set test;
HOSP_DIVISION = input(substr(HOSPSTCO, 1, 2) , $FIPS.);
HOSP_DIVISION2 = input(HOSPSTCO, $FIPS2.);
run;
What do you think the result should be to your boolean expressions that are comparing two strings with the OR operator? Let's test it and see what SAS does.
567 data _null_; 568 if '01' or '02' then put 'yes'; 569 else put 'no'; 570 run; NOTE: Character values have been converted to numeric values at the places given by: (Line):(Column). 568:6 568:14 yes
So it looks like it will convert those strings to numbers and do the OR. SAS will treat any value other than zero or missing as TRUE so your first IF test is going to always be true since all of the strings look like non-zero numbers.
If you want to compare one variable to any of a series of value using the IN operator. You can use the colon modifier on the IN operator just like you used it on the equals operator.
if HOSPSTCO in: ('23' '33' '50' '25' '44' '09') then ...
Why is this condition:
if HOSPSTCO=:'23' or '33' or '50' or '25' or '44' or '09' then HOSP_DIVISION=1;
always true?
Well, in a condition, the comparisons take precedence, then the NOT operator, then AND, then OR.
Therefore your condition translates to
if (HOSPSTCO=:'23') or ('33') or ('50') or ('25') or ('44') or ('09') then HOSP_DIVISION=1;
Since a boolean value needs to be numeric, the character values are converted on-the-fly, and since they all convert to non-zero and non-missing numbers, they are considered true, so this condition as a whole will always be true.
You want to use the IN operator and a set of values.
if HOSPSTCO=:'23' or '33' or '50' or '25' or '44' or '09' then HOSP_DIVISION=1;
This must generate quite a few note sin the log about type conversion.
These notes should never be tolerated: They indicate that the compiler finds data inconsistencies in the way a program is written
Remove the notes and the new program will work as expected.
Hint: HOSPSTCO=:'23'
is a Boolean number '
33
'
is also a Boolean number
It's finally time to hack! Remember to visit the SAS Hacker's Hub regularly for news and updates.
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.