好了,这周算是有些时间来更新一下咯~按照之前的约定,今天我就写一下sas宏的一些例子的解析,例子均为在学习中遇到的作业习题,是自己在初步学习sas宏之后写出来的,可能写得并不是最优的解法,若有,希望大家可以和我提出来呀嘻嘻~

话不多说,马上开始今天的sas宏的例子解析,今天我准备了一些例子,顺序也是按照难度来排的,会介绍一下宏的基本用法以及一些常见的错误,希望可以帮助到大家学习~
好了,之前有同学问我的sas代码颜色有什么含义,那我今天就统一解释一下。
/*这种颜色*/ :一般为注释,就是对这一行代码进行解释性说明,不会算入代码运行中;
proc:这种颜色一般为语法主体部分,一般出现在代码开头以及结尾;
output:这种颜色一般为语法中的关键字;
q1_age:这种就是普通代码了,没有什么特别含义,但也是最重要的东西。
例1:使用宏变量,对user表的age进行异常值检查,以1.5倍iqr作为异常值界限, 将含有异常值的记录以SAS数据集单独存储。
proc univariate data=hw1.Q3 noprint;/*proc univariate是sas中用于输出统计量的proc步常用过程*/
var age; /*设置你要统计的变量*/
output out=hw1.range_age /*设置输出数据集*/
q1=q1_age /*统计上界*/
q3=q3_age /*统计下界*/
QRANGE=iqr_age; /*统计iqr,即q3-q1的值*/
run;
/*使用data步定义宏,对q1,q3,iqr进行初始化*/
data _null_;
set hw1.range_age;
call symput('q3',q3_age);
call symput('q1',q1_age);
call symput('iqr',iqr_age);
run;
/*引用宏变量,并将输出结果输出到新数据集q41中*/
data hw1.q41;
set hw1.q3;
if age<&q1-1.5*&iqr|age>&q3+1.5*&iqr
then output;
run;
例2:使用宏来完成读取同一个文件夹下的所有数据集文件,并合并到同一张表(假设所有数据集的字段相同)
libname q4 'F:\指定文件夹地址';
%macro t; /*宏函数的开头*/
proc contents data=q4._all_ out=cnt(keep=memname) noprint nodetails; run; /*将q4文件夹里的所有数据集进行contents的输出,可以得到所有的数据集名称(memname)*/
proc sort data=cnt out=q4.cnt nodupkey;by MEMNAME;run;
proc sql;
select count(MEMNAME) into:maxobs
from q4.cnt; /*统计共有多少个数据集,用于后期循环最大次数的指定*/
quit;
data _null_;
set q4.cnt;
%do i=1 %to &maxobs; /*循环n次,n为数据集的数量*/
data _null_;
set q4.cnt(obs=&i firstobs=&i); /*读取第i条记录的观测值*/
call symputx("MEMNAME",MEMNAME); /*将读取到的观测值赋值给宏变量*/
run;
proc append base=q4.r data=q4.&MEMNAME.;run; /*使用append过程进行每次输出结果数据集的拼接*/
%end;
%mend; /*宏函数的结尾*/
%t; /*引用宏函数*/
例3:给定任意表,统计表内任意单个变量的分布,若变量为数值型变量,分布结果包含: 均值 , 标准差,众数, 缺失数,观测数, 0% 25% 50% 75% 100%分位数值,若为字符型变量,分布结果包含:变量值, 频数, 占比。
/*定义数值型处理的宏函数*/
%macro one_n(data=,var=,out=);
PROC UNIVARIATE data=&data;
VAR &var;
OUTPUT OUT=&out
mean=mean
STD=std
NMISS=NMISS
NOBS=NOBS
MODE=MODE
pctlpre=p pctlpts=(0 25 50 75 100);
run;
%mend one_n;
/*定义字符型处理的宏函数*/
%macro one_c(data=,var=,out=);
proc freq data=&data;
tables &var/out=&out;
run;
%mend one_c;
/*定义主函数,通过判断类型执行不同宏函数*/
%macro one(data=,var=,out=); /*指定宏函数的输入变量*/
proc contents data=&data out=cnt(keep=name type);run; /*对输入的变量data进行contents计算,得到这个数据集所有变量的数据类型type*/
proc sql;
select TYPE into:type1 from cnt
where NAME=propcase("&var"); /*将你要统计的变量var的数据类型赋值给type1*/
quit;
/*对type1进行类型判断,1为数值型,2为字符型,调用不同过程*/
%if &type1 = 1 %then
%do;
%one_n(data=&data,var=&var,out=&out); /*数值型变量的计算过程,也为宏,这里是直接引用宏的了,而这个宏的定义则在前面就已经定义的了*/
%end;
%else
%do;
%one_c(data=&data,var=&var,out=&out); /*字符型变量的计算过程,也为宏,这里是直接引用宏的了,而这个宏的定义则在前面就已经定义的了*/
%end;
%mend;
/*调用宏函数*/
%one(data=sashelp.class,var=name,out=a);
例4:给定任意表,统计表内所有变量的分布,按变量类型保存到任意指定的两张结果表,若变量为数值型变量,分布结果包含: 均值 , 标准差,众数, 缺失数,观测数, 0% 25% 50% 75% 100%分位数值,若为字符型变量,分布结果包含:变量值, 频数, 占比。
嘿嘿,这道题目其实是上一道题的进阶版,很有意思~
libname a 'C:\Users\Sam-Win\Desktop\SAS学习';
/*定义数值型处理的宏函数*/
%macro two_n(data=,var=,numout=,i=);
PROC UNIVARIATE data=&data noprint;
VAR &var.;
OUTPUT OUT=&&numout.&i.
mean=mean
STD=std
NMISS=NMISS
NOBS=NOBS
MODE=MODE
pctlpre=p pctlpts=(0 25 50 75 100);
run;
data &&numout.&i.;
set &&numout.&i.;
length name $10. ;
name="&var.";
label mean=mean;
label std = std;
label nmiss=missing;
label nobs=record;
label mode=mode;
label p0=p_0;
label p25=p_25;
label p50=p_50;
label p75=p_75;
label p100=p_100;
run;
proc append base=&numout. data=&&numout.&i force;run; /*将输出的结果集用append进行拼接,force关键字可以允许变量数量不同的情况下进行拼接/
%mend two_n;
/*定义字符型处理的宏函数*/
%macro two_c(data=,var=,charout=,i=);
proc freq data=&data noprint;
tables &var/out=&&charout.&i.;
run;
data &&charout.&i.;
set &&charout.&i.;
length varname $10. ;
varname="&var.";
rename &var=value;
label &var=value;
label COUNT = COUNT;
label PERCENT=PERCENT;
run;
proc append base=&charout. data=&&charout.&i. force;run;
%mend two_c;
/*定义主函数,通过判断类型执行不同宏函数*/
%macro two(data= ,numout=,charout=);
proc contents data=&data out=cnt(keep=name type);run;
proc sql;
select count(name) into:maxobs /*统计共有多少个变量,用于后期循环最大次数的指定,和例2有点像*/
from cnt;
quit;
data _null_;
set &data;
%do i=1 %to &maxobs; /*逐行读取观测,读取不同的变量,并将读取的观测值赋值给宏变量,用于后期的调用*/
data _null_;
set work.cnt(obs=&i firstobs=&i);
call symputx("varname",name);
call symputx("vartype",type);
run;
%if &vartype = 1 %then
%do;
%two_n(data=&data,var=&varname,numout=&numout,i=&i); /*相比上一道题,多了一个i变量*/
%end;
%else
%do;
%two_c(data=&data,var=&varname,charout=&charout,i=&i);
%end;
%end;
%mend;
/*调用宏函数*/
%two(data=sashelp.class,numout=a,charout=b);

好啦,今天就先讲这么多啦,下次计划讲一些sas的统计分析和时间序列模型的预测,主要还是一些描述性统计分析,参数估计与假设检验,方差分析,主成分分析与因子分析,聚类分析,判别分析,回归分析,logistic分析,时间序列分析等等啦,敬请期待!
”欢迎关注,嘻嘻~”
本文介绍了SAS宏的几个实例,包括使用宏变量进行异常值检查,批量合并数据集,统计单个变量和所有变量的分布。通过这些例子,详细讲解了宏的使用方法和常见操作,帮助读者深入理解SAS宏的运用。
5524

被折叠的 条评论
为什么被折叠?



