sas的TRANSPOSE过程详解
今天我第一次用到sas里面的TRANSPOSE过程,为此我查了一些资料,发现网上有些文章写的不是很清楚。下面我谈谈sas里面的TRANSPOSE过程。本文只在sas8.2下调试通过。
先看图,有些简陋。

sas transpose过程说明图
TRANSPOSE过程能实现sas数据集的转置,所谓转置,就是把观测(行)变成变量(列),变量变为观测,如上图中,从表1变成表3。该过程从读入的一个数据集中,创建一个新的数据集。具体用法格式如下:
PROC TRANSPOSE DATA=input-data-set LABEL=label LET NAME=name OUT=output-data-set PREFIX=prefix ; BY variable-1 ... variable-n ; COPY variable(s); ID variable; IDLABEL variable; VAR variable(s);
sas里的所有过程,都分为选项/option和声明statement两部分,在格式上,选项与过程名是一条语句,而每个声明单独成语句,也就是用分号分隔开。在程序运行上也一样,过程与选项一次性读入后分析。
很多时候,我们也许只用到几个选项,或者几个声明就实现了自己的目的,不过如果你能确切的了解每个过程的选项和声明,会让你的程序更加简洁易读。
以下是从sas support翻译过来的,并加入我自己的解释。
选项/Options
选项1:
DATA=input-data-set
需要进行转置的数据集的名字。 默认情况下,转置最近新建的数据集。
选项2:
LABEL= label英文的表述是:指定新输出的数据集中新观测的变量的标签,默认是_LABEL_,但是经过我的测试,这个选项没有任何意义,也就是设置与否不起任何作用。
选项3:
LET
允许重复的ID变量,并且当重复时,以最后一个为准,所谓的id变量,就是类上图中表1中name的作用,一般来讲,它的值不允许重复,因为如果重复,会导致生成重复变量。
选项4:
NAME= name指定新转置生成的数据集里新变量的名称。比如上图中转置后的表2和表三的第一列,也就是第一个变量的名称,如果不设置,会以name of former variable命名,设置后,该变量的标签名依然是name of former variable。我认为前面的label选项,就是用来设置该变量的标签的,但是设置后居然没有变化,不知道是我sas问题还是版本的问题。在上图表3中,我设置name为tnew,所以显示为tnew。在sas9.2版本中,改默认变量为_name_。
选项5:
OUT= output-data-set
输出数据集,也就是转置后的数据集的名称,默认以data后面加数字来命名。
选项6:
PREFIX= prefix前缀,原来观测变成变量后的前缀,不设置,也就是默认情况下,这些变量会以col1,col2排列下去,有的sas版本会以var1, var2排列下去。设置后,会以设置的字符串后加上数字1、2,并以此排列下去。为便于识别变量,这个选型经常与声明里的id混合使用,如表3,就是使用了id声明与前缀选项的结果。
例程如下,你可以copy到sas里查看运行结果。
data a; input name $ test1 test2 test3; cards; wyt 98 99 97 ycy 78 45 34 ynn 78 90 87 ; run; proc transpose data=a name=tnew label=n out=b let ; run; proc print data=a; run; proc print data=b; run;
声明/statement
下面是transpose过程的声明。声明使用的例程如下,比上面多的就是在选项之后,与run之间的声明部分。
data c; input name $ test1 test2 test3; cards; wyt 98 99 97 ycy 78 45 34 ynn 78 90 87 ; run; proc transpose data=a name=tnew label=n out=d prefix=t let ; id name; var name test1 test2; copy test3; run; proc print data=d; run; proc print data=c; run;
声明1:
BY variable-1 <... variable-n> ;
下面这张图,很清楚指明了分组转置是怎么样一个过程,其中的DESCENDING是以降序排列,而NOTSORTED,是不排序。此声明没在sas8.2下测试。

声明2:
ID variable(s);
在前面说过,prefix经常与此声明共同使用,该声明的作用就是,把新生成数据集里的变量用id的值表示出来,如上图中的表三,就是应用了id后把id的值一一指定。在sas的很多过程里均有id的概念,该值一般不重复,因此可以指定为变量,在sas数据集里,观测可以重复,变量不能重复。另外,这个声明还经常与下面的声明仪器出现。
声明3:
IDLABEL variable;用来指定上面对应变量的label,标签。
声明4:
VAR variable(s);
指明那几个变量进行转置,在本例子中,只讲test1与test2进行了转置,生成如下图的sas数据集。
声明5:
COPY variable(s);
这个声明用来原样拷贝源数据集中的某一个变量,原样不动的含义就是在新数据集里,改变量的值与源数据集中的一样,下面的例子,最后生成的数据集如下图所示,看着有点发懵,呵呵,在仔细看看就懂了

sas transpose statement
。
另外,当我要获取sas数据集的变量名并赋值给宏的时候,这篇文章帮了大忙,谢谢。具体内容转帖如下:
对一个数据集的变量进行分析,至少需要变量名,对吧。如果变量少,自已逐个输入也没问题,所谓忍一忍就和谐了。如果变量多呢,就无法忍受了–一个个地敲进去,不但麻烦,且易出错。解决之道有三种。
其一是读取表的dictionary.columns.Dictionary表里保存着库名及其成员的名字。以sashelp里的表class为例。
proc
sql;
create
table vars as
select varnum,name
from dictionary.columns
where memname=‘CLASS’;
quit;
其中varnum表示是第几个变量,name表示变量名。值得提醒的是,Dictionary里是以大写字母的形式保存表名。所以这里须要写CLASS。
其二是读取SASHELP.VCOLUMN。以数据步读取的形式如下
data vars1;
set sashelp.vcolumn;
where memname=‘CLASS’;
keep varnum name;
run;
其三是利用过程proc contents。这个要来得比读取dictionary和sashelp.vcolumn灵活。
data vars1;
set sashelp.vcolumn;
where memname=‘CLASS’;
keep varnum name;
run;
如果需要将变量名赋给一个宏变量,以空格隔开。其例如下
proc
contents
data=sashelp.class
out=vars3(keep=varnum name)
noprint;
run;
proc
sql
noprint;
select
distinct name
into :classname separated by
‘ ‘
from vars3
order
by varnum;
quit;
可以用%put &classname;察看其宏变量。得到结果
Name Sex Age Height Weight
当然有时并不想所有的变量都赋给这个宏变量。比如只想取出第1个和第2个变量给宏变量。当然也好解决。
proc
sql
noprint;
select
distinct name
into :classname separated by
‘ ‘
from vars3
where varnum in (1,2)
order
by varnum;
quit;
注意加了行where varnum in (1,2).或者
proc
contents
data=sashelp.class(keep=Name Sex)
out=vars4(keep=varnum name)
noprint;
run;
proc
sql
noprint;
select
distinct name
into :classname separated by
‘ ‘
from vars4
order
by varnum;
quit;
%put &classname;
也是一样的。








