如何让循环第一次做一件事,其他时候做另一件事

How to have loop do one thing first time and something else other times

假设我有这个数据:

clear
set more off
input ///
float (b a_first a_second a_third control)
4 3 2 5 7
6 3 4 2 4
7 6 5 2 5
1 4 2 3 6
7 6 1 4 1
8 8 7 4 4
end

我想使用 outreg2 创建一个 table:

foreach i in first second third {
    reg b a_`i'
    outreg2 using filename, replace
    reg b a_`i' control
    outreg2 using filename, append
}

(请注意,“文件名”是您选择的文件名。)这并不完全符合我的要求。对于每次迭代,它都会创建一个只有两列的 table。下一次,它用两个新的回归替换了原来的内容。

我需要它做的只是第一次替换,然后切换到追加:

reg b a_first
outreg2 using filename, replace
reg b a_first control
outreg2 using filename, append
reg b a_second
outreg2 using filename, append
reg b a_second control
outreg2 using filename, append
reg b a_third
outreg2 using filename, append
reg b a_third control
outreg2 using filename, append

我能想到的最好办法是创建一个局部变量,如果 i==first 取值 replace,并在第一个 outreg2 语句中使用这个局部变量。有没有更直接的方法?

考虑存储回归估计,然后在循环外使用outreg2,简明扼要地使用通配符[*]。见 Example 3 of the outreg2 doc:

foreach i in first second third {
    reg b a_`i'
    est store `i'
    reg b a_`i' control
    est store `i'control
}

outreg2 [*] using filename, replace

这几乎就是您的想法,但并不太难看,因为它只需要 运行 第一次使用以避免需要 if。我不会将此称为答案,但我还没有弄清楚如何 post 清理评论中的代码。

local rep replace
foreach i in first second third {
    reg b a_`i'
    outreg2 using filename, `rep'
    local rep append
    reg b a_`i' control
    outreg2 using filename, append
}

为了完整起见,请注意一个经典的替代方法,即在循环之外进行第一次迭代:

reg b a_first
outreg2 using filename, replace
reg b a_first control
outreg2 using filename, append


foreach v in second third { 
    reg b a_`v' 
    outreg2 using filename, append
    reg b a_`v' control
    outreg2 using filename, append
}