1

我的数据如下所示:

id t   x 
1  1  3.7 
1  3  1.2 
1  4  2.4 
2  2  6.0 
2  4  6.1 
2  5  6.2 

对于每个id我想根据需要添加观察结果,因此所有 1<=t<=5 都有值。

所以我想要的结果是:

id t   x 
1  1  3.7 
1  2  .
1  3  1.2 
1  4  2.4 
1  5  .
2  1  .
2  2  6.0 
2  3  .
2  4  6.1 
2  5  6.2 

我的真实设置涉及大量数据,所以我正在寻找最有效的方法来做到这一点。

4

3 回答 3

2

这可能是最简单的方法,使用 PROC Summary 中的 COMPLETETYPES 选项。我假设 id 和 t 的组合在数据中是唯一的。我唯一不确定的是在运行非常大的数据集时是否会遇到内存问题,我过去在这方面遇到过 PROC Summary 问题。

data have;
input id t x;
cards;
1  1  3.7 
1  3  1.2 
1  4  2.4 
2  2  6.0 
2  4  6.1 
2  5  6.2 
;
run;

proc summary data=have nway completetypes;
class id t;
var x;
output out=want (drop=_:) max=;
run;
于 2013-02-13T09:00:03.903 回答
1

这是另一种方法,前提是您已经知道 T 的最小/最大值。它创建一个包含 ID 和 T 的所有值的模板,然后与原始数据集合并,以便保留 X 的值。

proc sort data=original_dataset out=template(keep=id) nodupkey;
   by id;
run;

data template;
   set template;
   do t = 1 to 5; /* you could make these macro variables */
      output;
   end;
run;

proc sort data=original_dataset;
   by id t;
run;

data complete_dataset;
   merge template(in=in_template) original_dataset(in=in_original);
   by id t;
   if in_template then output;
run;
于 2013-02-12T23:05:29.117 回答
1

如果您有 ETS,一种选择是使用 PROC EXPAND。我不确定它是否能 100% 完成你想要的,但这可能是一个好的开始。到目前为止,主要问题似乎是它不会在开始或结束时进行记录,但我认为这是可以克服的;只是不确定如何。

proc expand data=have out=want from=daily method=none extrapolate;
by id;
id t;
run;

它为 id 1 填写 2,为 id 2 填写 3,但不为 id 1 填写 5 或为 id 2 填写 1。

要在基本 SAS 中执行此操作,您有几个选择。带有 SPARSE 选项的 PROC FREQ 可能是一个不错的选择。

proc freq data=have noprint;
tables id*t/sparse out=want2(keep=id t);
run;

data want_fin;
merge have want2;
by id t;
run;

您也可以通过 PROC SQL 执行此操作,并使用可能的 t 值连接到表,但这对我来说似乎较慢(即使 FREQ 方法需要两次通过,FREQ 将非常快并且合并使用已经排序的数据所以这也不是太慢)。

于 2013-02-12T19:14:13.193 回答