为特定日历日创建虚拟变量

时间:2014-07-31 16:51:51

标签: date stata

在Stata中,我想为该月的第25个日历日生成一个指标,如果该日历日属于周末或假日,则生成前一个工作日。我在Stata中使用商业日历,在非工作日产生缺失值。

最有效的脚本是什么,而不是迭代地做这样的事情:

gen d25 = d == 25
replace d25 = cond(d[_n+1]==25 & date[_n+1]==.,1,d25)

Etc... 

2 个答案:

答案 0 :(得分:2)

这是一个如何做到这一点的例子:

sysuse sp500, clear
keep date

gen in_bcal=1
tsset date
tsfill
gen day25=cond(day(date)==25,1,0)
drop if missing(in_bcal) & day25==0 
sort date
replace day25=day25[_n+1] if missing(in_bcal[_n+1])
drop if missing(in_bcal)
drop in_bcal

这可能会以更聪明的方式完成。

答案 1 :(得分:2)

作为@Dimitriy答案的补充,我想解决两个问题:

1。我对原始海报问题的解释是他开始使用商业日历。因此,问题在于标记商业日历中可能存在或不存在的一个月中的任意日期(数字)。如果它不存在,那么我们标记前一个工作日。

如果是这种情况,那么我们需要对原始代码进行少量添加,因为如果涉及业务日历,tsfill将无法按预期工作。 (sp500数据库date变量不是describe将显示的业务日历。)例如:

clear all
set more off

*----- example data -----

set obs 19

gen bdate = _n
format bdate %tbsimple // format as "simple" business calendar

*----- tsfill -----

tsset bdate
tsfill

list
在这种情况下,

tsfill不会填写任何内容;它不会填写非工作日。这些日子已被日历划掉,因此无需填写。我们需要:

gen rdate = dofb(bdate, "simple")
format rdate %td

商家日历日期转换为常规日期。然后我们可以使用常规日期变量rdate继续使用像Dimitriy这样的代码。

2。第二个问题是,如果系列的最后一次观察恰好是我们想要标记的那一天,那么Dimitriy的代码将导致丢失。这可以通过查找第31天而不是25来检查。2001年12月将缺少第31天。

下面是一个解决这两个问题的完整示例,希望不会增加任何错误。当然,Dimitriy对于一般(正确)的想法都很有用,任何错误都是我自己的。

clear all
set more off

*----- example data -----

set obs 19

gen bdate = _n
format bdate %tbsimple // format as "simple" business calendar

list, sep(0)

*----- what you want -----

gen rdate = dofb(bdate, "simple") // from business to regular
format rdate %td

tsset rdate
tsfill

gen day6 = (day(rdate) == 6)

drop if missing(bdate) & !day6
replace day6 = 1 if missing(bdate[_n+1]) & day6[_n+1] == 1
drop if missing(bdate)

list, sep(0)