1

我正在尝试为 1996 年到 2012 年(含)的每一年生成一个虚拟变量,这样如果是 1996 年,则 1996 年的虚拟变量应该等于 1,如果使用foreachStata 中的命令来缩短时间(至少对于未来的项目),则应该等于 0 )。目前正在发生的情况是正在生成 1996 年的虚拟模型,但没有生成其他模型。我认为这与我的定义方式有关j,但我无法完全弄清楚格式以达到我想要的结果。我在网上和 Stata 帮助文件中查看过,找不到关于这个特定主题的任何内容。

到目前为止,这是我所拥有的:

local var year
local j = 1996
foreach j of var year {
    gen d`j' = 1 if year==`j'
    local ++j
}

我将继续尝试自己解决这个问题,但如果有人有建议,我将不胜感激。

4

3 回答 3

5

让我们逐行看这个。

local var year

var您用 content定义了一个本地宏"year"。这是合法的,但您从不在此代码中引用该本地宏,因此该定义毫无意义。

local j = 1996

j您用 content定义了一个本地宏"1996"。这是合法的。

foreach j of var year {

您打开一个循环并将循环索引定义为j。这意味着在循环中对本地宏的任何引用j都将根据您提供的参数列表进行解释。(前面的定义j在循环中是不相关的,因此对你的其余代码没有影响。)

... of var year 

您在此处指定循环在变量列表上。请注意,var这里的关键字是缩写,与您刚刚定义varlist的本地宏名称完全无关。var变量列表由单个变量名组成year

gen d`j' = 1 if year==`j'

该语句将被解释为循环执行的唯一一次,如

gen dyear = 1 if year==year 

因为对局部宏的引用j被替换为它的内容,即变量名yearyear==year对于每个观察都是正确的。效果是一个新变量dyear,在每个观察中都是 1。这不是您想要的指标或虚拟变量。如果您仔细查看数据集,您会发现这不是year1996 年的虚拟变量。

local ++j

您正在尝试将本地宏j增加 1。但您只是将本地宏设置j为包含字符串"year",这是一个变量名。但是您不能将 1 添加到字符串中,因此错误消息将为type mismatch. 您没有报告该错误,这是一个惊喜。这有点微妙,因为在前面的命令中,上下文generate允许将引用解释为year使用变量 计算的指令,变量year自然是数字。但是local命令都是关于字符串操作的,它可能有也可能没有数字解释,你的命令首先等同于指示 Stata 添加

"year" + 1 

这会触发类型不匹配错误。

远离你的代码:考虑一个循环

forval y = 1996/2012 { 
    gen d`y' = 1 if year == `y'
} 

这更接近您想要的,但更清楚地说明了代码中的另一个错误。这将创建变量d1996d2012但每个变量在指定的年份都为 1,否则会丢失,这不是您想要的。您可以通过在循环中添加另一行来解决此问题

    replace d`y' = 0 if year != `y' 

但更清洁的方法是单行

    gen d`y' = year == `y' 

表达方式

               year == `y' 

当为真时被评估为 1,当为假时被评估为 0,这就是你想要的。

所有这些都是在 [U] 或 [P] 中记录的标准技术。

然而,正如@Roberto Ferrer 指出的那样,有经验的 Stata 用户不会以这种方式定义假人,因为tabulate它提供了一个选项,可以在没有循环的情况下进行。

http://www.stata-journal.com/sjpdf.html?articlenum=pr0005中汇集了对本地宏foreachforvalues循环的评论的教程

 search foreach 

在 Stata 中会指出这是您可以阅读的各种作品之一。

于 2014-05-03T00:35:23.250 回答
3

循环不是必需的。尝试使用该选项的tabulate命令。gen()help tabulate oneway

另见help xihelp factor variables

您正在尝试遍历不同的值,year但语法不正确。您实际上是在循环一个只有一个元素的变量列表:year. 该命令levelsof为您提供不同的值,但就像我说的,循环不是必需的。

于 2014-05-02T22:51:56.907 回答
0

也许这可能会有所帮助。

/*assuming the data is from 1970-2012*/
/*assuming your year variable name is fyear*/

forvalues x=1970/2012 {  
gen fyear `x'=0
replace fyear `x'=1 if fyear==`x' 

}

但是,我确实同意 Roberto Ferrer 的观点,即循环可能不是必需的。

于 2014-09-10T10:50:14.627 回答