如何在 SAS 中计算出宏变量的数据类型
How do I work out the data type of my macro variable in SAS
如何在日志中打印出宏变量的数据类型
%macro mymacro(dt2);
%LET c_mth = %SYSFUNC(intnx(month,&dt2.d,-1,e),date9.) ;
%put &c_mth;
%mend;
mymacro('01sep2014')
我有一堆使用 %let 或 into 分配的宏变量:
我的问题是我试图在日期上做一堆布尔条件,但我怀疑我的一些变量是字符串,一些是日期
我已将它们放入我的代码中,但要进行三重检查,肯定有一种方法可以将 return 某些内容写入日志
我想要类似于在 R
中使用 str() 或 mode() 或 is.numeric() 的东西
宏变量没有类型,都是文本。
您必须确保以对程序有意义的方式传递变量并生成有效的 SAS 代码。
%let date1=01Jan2014;
%let date2=31Jan2014;
data _null_;
x = "&date1"d > "&date2"d;
y = "&date2"d > "&date1"d;
z = "&date2"d-"&date1"d;
put 'x=' x;
put 'y=' y;
put 'z=' z;
run;
日志应显示:
x=0
y=1
z=30
H,
SAS 宏语言很奇怪。 :)
正如Reeza所说,宏变量没有类型,它们都是文本。
但是,如果您使用布尔逻辑(%IF 语句),并且两个操作数都是整数,则宏语言将进行数字比较而不是字符比较。
因此您可以使用 INPUTN() 函数将日期字符串转换为 SAS 日期(自 1960 年 1 月 1 日以来的天数),然后进行比较。这是一个示例,从您的代码开始:
%macro mymacro(dt1,dt2);
%local c_mth1 c_mth2 n_mth1 n_mth2;
%let c_mth1 = %sysfunc(intnx(month,&dt1.d,-1,e),date9.) ;
%let c_mth2 = %sysfunc(intnx(month,&dt2.d,-1,e),date9.) ;
%let n_mth1 = %sysfunc(inputn(&c_mth1,date9.)) ;
%let n_mth2 = %sysfunc(inputn(&c_mth2,date9.)) ;
%put &c_mth1 -- &n_mth1;
%put &c_mth2 -- &n_mth2;
%if &n_mth1<&n_mth2 %then %put &c_mth1 is before &c_mth2;
%else %put &c_mth1 is NOT before &c_mth2;
%mend;
来自示例调用的日志:
236 %mymacro('01feb1960','01mar1960')
31JAN1960 -- 30
29FEB1960 -- 59
31JAN1960 is before 29FEB1960
--Q.
如果您的宏变量解析为日期文字,您可以使用 intck
结合 %eval
来比较它们,例如
%let mvar1 = '01jan2015'd;
%let mvar2 = '01feb2015'd;
/*Prints 1 if mvar2 > mvar1*/
%put %eval(%sysfunc(intck(day,&mvar1,&mvar2)) > 0);
如何在日志中打印出宏变量的数据类型
%macro mymacro(dt2);
%LET c_mth = %SYSFUNC(intnx(month,&dt2.d,-1,e),date9.) ;
%put &c_mth;
%mend;
mymacro('01sep2014')
我有一堆使用 %let 或 into 分配的宏变量: 我的问题是我试图在日期上做一堆布尔条件,但我怀疑我的一些变量是字符串,一些是日期 我已将它们放入我的代码中,但要进行三重检查,肯定有一种方法可以将 return 某些内容写入日志
我想要类似于在 R
中使用 str() 或 mode() 或 is.numeric() 的东西宏变量没有类型,都是文本。
您必须确保以对程序有意义的方式传递变量并生成有效的 SAS 代码。
%let date1=01Jan2014;
%let date2=31Jan2014;
data _null_;
x = "&date1"d > "&date2"d;
y = "&date2"d > "&date1"d;
z = "&date2"d-"&date1"d;
put 'x=' x;
put 'y=' y;
put 'z=' z;
run;
日志应显示: x=0 y=1 z=30
H,
SAS 宏语言很奇怪。 :)
正如Reeza所说,宏变量没有类型,它们都是文本。
但是,如果您使用布尔逻辑(%IF 语句),并且两个操作数都是整数,则宏语言将进行数字比较而不是字符比较。
因此您可以使用 INPUTN() 函数将日期字符串转换为 SAS 日期(自 1960 年 1 月 1 日以来的天数),然后进行比较。这是一个示例,从您的代码开始:
%macro mymacro(dt1,dt2);
%local c_mth1 c_mth2 n_mth1 n_mth2;
%let c_mth1 = %sysfunc(intnx(month,&dt1.d,-1,e),date9.) ;
%let c_mth2 = %sysfunc(intnx(month,&dt2.d,-1,e),date9.) ;
%let n_mth1 = %sysfunc(inputn(&c_mth1,date9.)) ;
%let n_mth2 = %sysfunc(inputn(&c_mth2,date9.)) ;
%put &c_mth1 -- &n_mth1;
%put &c_mth2 -- &n_mth2;
%if &n_mth1<&n_mth2 %then %put &c_mth1 is before &c_mth2;
%else %put &c_mth1 is NOT before &c_mth2;
%mend;
来自示例调用的日志:
236 %mymacro('01feb1960','01mar1960')
31JAN1960 -- 30
29FEB1960 -- 59
31JAN1960 is before 29FEB1960
--Q.
如果您的宏变量解析为日期文字,您可以使用 intck
结合 %eval
来比较它们,例如
%let mvar1 = '01jan2015'd;
%let mvar2 = '01feb2015'd;
/*Prints 1 if mvar2 > mvar1*/
%put %eval(%sysfunc(intck(day,&mvar1,&mvar2)) > 0);