我想我之前发过类似的问题。但这次我正在努力解决数据ID问题。
我的数据看起来像
date Stock value standard_deviation
01/01/2015 VOD 18 ...
01/01/2015 VOD 15 ...
01/01/2015 VOD 5 ...
03/01/2015 VOD 66 ...
03/01/2015 VOD 7 ...
04/01/2015 VOD 19 ...
04/01/2015 VOD 7 ...
05/01/2015 VOD 3 ...
06/01/2015 VOD 7 ...
..... ... ... ...
01/01/2015 RBS 58 ...
01/01/2015 RBS 445 ...
01/01/2015 RBS 44 ...
03/01/2015 RBS 57 ...
我需要根据(-3,+ 3)交易日计算每只股票的移动平均线/标准差
。由于那些是交易日(不是日历日),并且每天有不同的交易数量,我创建了一个子查询并应用了以下代码。
data want;
set input;
by date;
retain gdate;
if first.date then gdate+1;
run;
proc sort data=want; by stock gdate ; run;
proc sql;
create table want1 as
select
h.stock,
h.date,
h.value,
( select std(s.value) from want s
where h.gdate between s.gdate-2 and s.gdate+2) as std
from
want h
group by stock;
quit;
我试过了group by stock
。但是,代码忽略了股票组,只给了我整个期间的移动标准。我需要针对不同股票的移动标准 。
任何人都可以给我一些想法吗?谢谢!
答案 0 :(得分:3)
让我们熟悉PROC EXPAND
!它会在时间序列中成为你最好的朋友。
PROC EXPAND
可让您对数据进行basically all of the common transformations (and even ones you didn't know existed)。
首先,回答你的问题:
第1步:将每个股票的所有价值合并为一个交易日
proc sql noprint;
create table have2 as
select date, stock, sum(value) as total_value
from have
group by stock, date
order by stock, date;
quit;
步骤2:使用PROC EXPAND计算+/- 3天居中移动标准差
proc expand data=have2
out=want;
id date;
by stock;
convert total_value = standard_deviation / transform=(cmovstd 7);
run;
第3步:合并回原始表
proc sort data=have;
by stock date;
run;
data want2;
merge have
want;
by stock date;
run;
<强>解释强>
我们正在利用分组处理和现有程序来为我们完成大部分工作。由于语言的设计方式,SAS喜欢并不喜欢向前看,PROC EXPAND
是极少数能够在没有大量额外工作的情况下向前看数据的程序之一。此过程的另一个好处是,如果时间序列中存在间隙,它不会中断,因此您可以对任何类型的顺序数据执行操作。
其中一个转换操作cmovstd
将为我们应用数据的居中移动标准偏差,以便实现收集移动标准偏差的未来数据。请注意,我们选择了一个7的窗口来获得+/- 3天居中的移动标准偏差。那是因为我们需要:
3 past days | +3
current day | +1
3 future days | +3
| 7 = window size
或者,在我们的窗口共7天。如果您想要一个+/- 2天居中的移动标准偏差,您的窗口将是5:
2 past days | +2
current day | +1
2 future days | +2
| 5 = window size
如果您选择偶数,您将有一个或多个滞后天来使窗口选择有效。例如,窗口4将产生:
2 past days | +2
current day | +1
1 future day | +1
| 4 = window size
PROC EXPAND
就像瑞士军刀的时间序列。它将在一个步骤中插入,外推,转换和转换时间段。在以下情况下,您可能会发现它最有用:
<强> 1。应用移动(平均值,标准等)
proc expand data=have
out=want;
<by variable(s)>;
id <date variable>;
convert <numeric variable(s)> = <new variable name> / transform=(<operation> <window>);
run;
<强> 2。填补时间空白
proc expand data=have
out=want
to=<day, month, year, etc.>;
<by variable(s)>;
id date;
convert <numeric variable(s)> </method=<interpolation method> >;
run;