Reputation: 7167
I have a set of 18 Stata data files (one per year) whose names are:
{aindresp.dta, bindresp.dta, ... , rindresp.dta}
I want to eliminate some variables from each dataset. For this, I want to use the fact that many variables across dataset have the same name, plus a prefix given by the dataset prefix (a, b, c, ... r). For example, the variable rach12
is called arach12
in dataset aindresp.dta
, etc. Thus, to clean each dataset, I run a loop like the following:
clear all
local list a b c d e f g h i j k l m n o p q r
foreach var of local list {
use `var'indresp.dta
drop `var'rach12 `var'jbchc1 `var'jbchc2 `var'jbchc3 `var'xpchcf var'xpchc
save `var'indresp.dta, replace
}
The actual loop is much larger. I am deleting around 200 variables.
The problem is that some variables change name over time, or disappear after a few years. Other variables are added. Therefore, the loop stops as soon as a variable is not found. This is because the drop
command in Stata stops. Yet, that command has no option to force it to continue.
How can I achieve my goal? I would not like to go manually over each dataset.
Upvotes: 3
Views: 6379
Reputation: 37183
help capture
You can just put capture
in front of the drop
. You can just keep going, but a little better would be to flag which datasets fail.
In this sample code, I've presumed that there is no point to the save, replace
if you didn't drop
anything. The basic idea is that a failure of a command results in a non-zero error code accessible in _rc
. This will be positive (true) if there was a failure and zero (false) otherwise.
A more elaborate procedure would be to loop over the variables concerned and flag specific variables not found.
clear all
local list a b c d e f g h i j k l m n o p q r
foreach var of local list {
use `var'indresp.dta
capture drop `var'rach12 `var'jbchc1 `var'jbchc2 `var'jbchc3 `var'xpchcf var'xpchc
if _rc {
noisily di "Note: failure for `var'indresp.data"
}
else save `var'indresp.dta, replace
}
See also Does Stata have any `try and catch` mechanism similar to Java?
EDIT:
If you want to drop
whatever exists, then this should suffice for your problem.
clear all
local list a b c d e f g h i j k l m n o p q r
foreach var of local list {
use `var'indresp.dta
capture drop `var'rach12 `var'jbchc1 `var'jbchc2 `var'jbchc3 `var'xpchcf var'xpchc
if _rc {
di "Note: problem for `var'indresp.data"
checkdrop `var'rach12 `var'jbchc1 `var'jbchc2 `var'jbchc3
}
save `var'indresp.dta, replace
}
where checkdrop
is something like
*! 1.0.0 NJC 1 April 2016
program checkdrop
version 8.2
foreach v of local 0 {
capture confirm var `v'
if _rc == 0 {
local droplist `droplist' `v'
}
else local badlist `badlist' `v'
}
if "`badlist'" != "" {
di _n "{p}{txt}variables not found: {res}`badlist'{p_end}"
}
if "`droplist'" != "" {
drop `droplist'
}
end
Upvotes: 5