SAS 9.4 字符函数 - 为什么一个单元格 return 可能会出现意外结果?

SAS 9.4 Character functions - Why might one cell return unexpected results?

我正在处理一些字符串变量,某些单元格使用子字符串和长度函数返回意外值。这些单元格保存字符格式的日期,因为我需要在将它们转换为 SAS 日期之前进行一些操作,因为它们来自 Excel 文件的性质。这是一个例子:

拥有:
Obs _orig
1 4/3
2 12/16
3 1/13
4 6/2
5 3/10
6 5/4
7 10/14

想要:
Obs _orig _length _sub_1_2
1 4/3 3 4/
2 12/16 5 12
3 1/13 4 1/
4 6/2 3 6/
5 3/10 4 3/
6 5/4 3 5/
7 10/14 5 10

我正在使用此代码:

data want;
set have;
_strip=strip(_orig);
_sub_1_2=substr(_strip,1,2);
_length=length(_strip);
run;

这就是我得到的。差异以粗体显示。
Obs _orig _length _sub_1_2
1 4/3 5
2 12/16 5 12
3 1/13 4 1/
4 6/2 3 6/
5 3/10 4 3/
6 5/4 5
7 10/14 5 10

这两种情况都是 SAS 在长度应 = 3 时计算出长度 = 5。在这两种情况下,子字符串派生变量的值完全为空。如果我在代码中使用 compress()、trim() 或 trimn() 而不是 strip(),结果是相同的。感谢您提供的任何帮助

听起来您的数据中可能有不可打印的字符。如果你 PUT _orig $hex.; 到日志,你会看到什么?应该是:342F332020

152  data want;
153   length orig ;
154   orig='4/3';
155   len=length(orig);
156   put orig= len=;
157   put orig hex.;
158  run;

orig=4/3 len=3
342F332020

要去除不可打印的字符,您可以尝试:

_strip=compress(orig,,'kw');

我很清楚你的变量有前导 spaces 或其他在屏幕上看起来像 spaces 的前导字符。因此,对于 OBS=6,字符串的值更像是长度为 5 的 " 5/4",前两个字符看起来都像 spaces。如果您的新 _sub_1_2 变量的 LENGTHN() 不为 0,那么它在那里有一些非打印字符。也许像 'A0'X 这样的东西,一些网页用作不间断的 space 或制表符('09'x)。

我怀疑您不想要前两个字符,而是在使用 / 作为分隔符时想要第一个单词。您可以使用 LEFT() 或 STRIP() 函数删除前导空格。或 COMPRESS() 删除其他垃圾。因此,您可以将 COMPRESS() 与 kd 修饰符一起使用,以仅保留数字和斜杠。

data want;
  set have;
  length first  ;
  first = scan(compress(_orig,'/','kd'),1,'/');
run;