(转)
在SAS处理中,特别是在多个数据集合并过程中,我们经常要遇到 日期格式不匹配的情况,但是 日期 又是一个非常关键的
匹配关键词,所以有必要 将各种不同的 日期变量的 转化 方法在这里做一个总结,不周到之处请广大博友提出修改意见。
1. input: 年月日
output: 年月 ,这里要区分 显示 和
实际值 的区别。
输入的时候,有时是数值型,我们可能要将其
转化为字符型,然后再定义其 日期的显示格式;
比较常用的命令:
数值格式转化为字符型: put(year(date),z4.0) ||'-'||
put(month(date),z2.0);
字符格式转化为日期型:input(date,yymmdd10.)
Formats:
DATEw.
date9.
01JAN2014
DDMMYYw.
YYMMDDw.
YYMMDD10.
2014-06-18
YYMMxw.
YYMONw.
put
x yymon7.;
2012JAN
Functions:
DAY
MONTH
MDY
date=mdy(1,2,2001);
2001-01-02
YEAR
季度:QTR(DATE)
今天日期返回函数:TODAY()
data test;
input time yymmn6.;
date=time-1;
format date yymmd7. time yymmd7.;
cards;
201201
201202
201203
201204
201205
;
run;
Data RiskFreeRateByMonth;
SetRiskFreeRateByMonth;
year_month=put(year(date),z4.0) ||'-'||
put(month(date),z2.0);
Proc print data=_last_(obs=25);
Run;
We can also use the “YYMMD.” format to do the same thing
For example:
year_month=put(date,YYMMD.);
data data _null_;
x='7jan2012'd;
put
x yymm7.;
put
x yymmc7.;
put
x yymmd7.;
put
x yymmn6.;
put
x yymmp7.;
put
x yymms7.;
put
x yymon7.;
run;
2012M01
2012:01
2012-01
201201
2012.01
2012/01
2012JAN
data a;
format date yymmdd10.;
date=mdy(1,2,2012);
yymm=compress(year(date)||month(date));
time=input(yymm,yymmn6.);
date1=time-1;
format
date1
yymmd7.;
format
time
yymmn6.;
run;
data a;
format date yymmdd10. time yymmd7. date1
yymmd7.;
date=mdy(1,2,2001);
time=input(put(date,yymmn6.),yymmn6.);
date1=time-1;
run;
%let e=3;
data a;
format date yymmdd10. time yymmd7. date1
yymmd7.;
date=mdy(1,2,2001);
time=input(put(date,yymmn6.),yymmn6.);
do i=1 to &e;
date1=intnx('month',time,-i);
output;
end;
run;
时间序列生成年月数据:
DATA zuoye7;
SET dd.cpi;
month=intnx('month','01NOV2009'd,_n_+1) ;
format month monyy7.;
proc print;
title '加入变量Month后的数据集输出';
run;
substr(put(date(),yymmddn8.),1,6)
运行后得到201207, 这个是当月的月份,请问如何得到上月的月份呢,运行后应该得到201206
substr(put(intnx('month',date(),-1),yymmddn8.),1,6)
data b;
set tmp;
mon=substr(put(left(date),7.),6,2);
year=substr(put(left(date),7.),1,4);
day='01';
time=MDY(mon,day,year);
informat time
yymmdd10.;
format time
yymmdd10.;
drop date mon year
day;
rename
time=date;
run;
临床试验数据中常包含很多日期数据,而且这些数据往往是年、月、日分开的,即用了三个变量分别存放年、月和日。现在要把它们组合在一起并以常用形式表现出来,以便后续计算和阅读。
假设源数据的年、月、日数据分别存放于三个变量year、month和day中。
第一步: 组合: 把年月日三个数据合并起来存放于变量date中
程序:
data a;
input
year month day;
date
= mdy (month,day,year); datalines;
1921 7 1
1949 10 1
1997 7 1
2006 7 31
2007 6 29
;
run;
注意到mdy()函数是实现这一步的关键。该函数就是为我们转换日期用的。非常好用。
mdy()函数需要三个参数,这三个参数的排列顺序固定,中间用“,”号分隔,即:
月,日,年。这里的月日年即可以是数字,如1997年6月28日就是mdy(6,28,1997),也可以是变量名,如本例。
有的时候,源数据的年月日的类型是文本型的,这也不用怕,用下面的程序解决。
data a;
input
year$ month$ day$;
date
= mdy(input(month,8.),input(day,8.),input(year,8.));
datalines;
1921 7 1
1949 10 1
1997 7 1
2006 7 31
2007 6 29
;
run;
注意到在mdy()函数中又嵌套了一个函数input()。input()函数的用处是把文本型数字转换成数值型数字(呵呵,有点怪是不?但实际工作中经常会碰到)。该函数有两个参数,前面一个是包含被转换数字的变量(名),后面一个是转换后数据的格式(关于格式可多了去了,有兴趣大家自己看吧,本例的格式是最简单的数值型8位)。
第二步: 表现:
将时间日期用常用的表现方式表现出来
在这里我必须要说明,由于时间日期的表现方式实在太多,我们只给大家介绍三个认识一下。
在上一步中,无论源数据中的年月日是文本型的还是数值型的,在新生成的SAS数据集a中都已经被组合到一起并存放到数值型变量date中了。注意这些数据与一般数据无异,但它们是与源数据中的年月日一一对应的。SAS把1960年1月1日作为基准,所有日期与这一基准的差转换成天数存放。如果早于1960年1月1日,差为负数,如果晚于1960年1月1日,差为正数。
我选了三种日期表现形式,用print过程输出,其程序和结果如下:
程序:
data b;
set
a;
date1
= date; date2
= date;
date3
= date;
proc print data=b noobs; format
date1 date9. date2 mmddyy10. date3
yymmdd10.; run;
输出:
SAS
システム 2007年
6月29日 金曜日
08:44 2
year month day date date1 date2 date3
1921 7 1 -14063 01JUL1921 07/01/1921 1921-07-01
1949 10 1 -3744 01OCT1949 10/01/1949 1949-10-01
1997 7 1 13696 01JUL1997 07/01/1997 1997-07-01
2006 7 31 17013 31JUL2006 07/31/2006 2006-07-31
2007 6 29 17346 29JUN2007 06/29/2007 2007-06-29
注意date变量值虽然与一般数字无异,但与同一记录中的年月日是一一对应的。后面date1到date3是同一日期的三种表现形式,其中有我们中国人习惯的年月日形式。
如果数据是用两位数来表示年份的需要设置前两位属于那个世纪
eg:08/14/83
需要通过设置世纪来让SAS知道是1983或者是1783或者2083
SAS默认的是两位数日期在1920到2019 之间 即当两位数年份用20-99时SAS认为是1920-1999年
当两位数年份是00-19时SAS认为是2000-2019年
要改变默认设置可以通过OPTINS进行
在SAS中输入
OPTIONS
yearcutoff=1950;
即可把SAS默认的两位数日期改为1950-2049年之间
OPTIONS
yearcutoff=1700
把SAS默认的两位数日期改为1700-1799年之间
(4)SAS的日期值之间可以进行加减运算从而可以方便的求出两个日期之间间隔多少天
futherdate=checkdate+21
可以求出checkdate21天后的日期是什么
(5)日期函数
day()、month()、qrt()、year()、weekday()可以分别从SAS日期值返回日
、月、季、年、和星期
mdy(m,d,y)可以求出SAS日期值
yrdif(stardate,enddate,'actual')可以返回两个日期之间的真实间隔天数
在sas中用sql过程的时候,如何把数字转为日期?
如:想查2004年4月1日到20111年4月的数据.
proc sql;
create table index.volindex as
select date, vix,vxo,vxn,vxd from index.cboe_vol_index
where date between ‘01apr2004’d
and
‘30apr2011’d;
quit;
如果原数据中date是字符型
where substr(date,1,8)
between '20040401' and
'20110430';
2. 数值型 转化为 日期型:
我的问题是原始的数据库里有一个Date变量,为11.的数值型,形如20120304
我想把它变为日期型,如yymmdd10.,形如2012-03-04
?
data
new;
input
date 11.;
date_1=mdy(mod(int(date/100),100),mod(date,100),int(date/10000));
format
date_1 yymmdd10.;
put
date_1 yymmdd10.;
datalines;
20010101
20020305
;
run;
或者:
data new;
input date 11.;
date_1=input(put(date,z8.),yymmdd10.);
format date_1 yymmdd10. ;
datalines;
20010101
20020305
;
run;
如何将形如20010101,20020305这样的数值型变量转换成日期型变量呢?
data x;
input k;
cards;
19840123
;
run;
data y;
set x;
a=compress(trim(k));
length z1 $10.;
z1=compress(substr(a,1,4)||'-'||substr(a,5,2)||'-'||substr(a,7,2));
z2=mdy(substr(a,5,2),substr(a,7,2),substr(a,1,4));
format z2 yymmdd10.;
run;
data new;
input date yymmdd8.;
format date date9.;
datalines;
20010101
20020305
;
proc print;run
;
data test;
input num;
date =
input(put(num, 8.), YYMMDD8.);
format date
YYMMDD10.;
cards;
20010101
20020305
19970701
;
proc print;
run;
3.日期型转化为数值型:
SAS中的日期数据转化为数值型
SAS中的日期数据比如,2004-04-15,转换为数值型的20040415?
date=compress(date,'-');
date1=input(date,yymmdd10.);
informat date1 yymmdd10.;
format date1 yymmdd10.;
drop date;
rename date1=date;
label date1='date';