bvowe
bvowe

Reputation: 3394

Identify first event or last non-event

I have the following data in Stata:

clear

* Input data
input float id str7 event time
id  event   time
1   "." 10
1   "." 20
1   "1" 30
1   "0" 40
1   "." 50
2   "0" 10
2   "0" 20
2   "0" 30
2   "0" 40
2   "0" 50
3   "1" 10
3   "1" 20
3   "0" 30
3   "." 40
3   "." 50
4   "." 10
4   "." 20
4   "." 30
4   "." 40
4   "." 50
5   "1" 10
5   "1" 20
5   "1" 30
5   "1" 40
5   "1" 50     
end

Below is data I hope to get to:

* Input data
input float id str7 event time
id1 event1  time1
1   1   30
2   0   50
3   1   10
4   .   50
5   1   10

end

My aim is to take the first row for each id of an event equal to 1. If an id has no event for any time, then I want to report the last time of the report.

Upvotes: 0

Views: 302

Answers (3)

Nick Cox
Nick Cox

Reputation: 37358

This is based on an answer by Romalpa Akzo on Statalist:

bys id (time): gen tag = 1 if  event == "1" | _n ==_N
bys id (tag time): keep if _n == 1
drop tag

I think that's the neatest answer to date. Note how it hinges on tag being missing if it is not 1.

Upvotes: 1

user8682794
user8682794

Reputation:

The following works for me:

replace event = "-1" if event == "1"

bysort id (event time): generate tag1 = event[_n==1] == "-1" 
bysort id (event time): generate tag2 = event[_n==_N] == "0" 
bysort id (event time): generate tag3 = event[_n==_N] == "."

replace event = "1" if event == "-1"
keep if tag1 == 1 | tag2 == 1 | tag3 == 1

list

     +----------------------------------------+
     | id   event   time   tag1   tag2   tag3 |
     |----------------------------------------|
  1. |  1       1     30      1      0      0 |
  2. |  2       0     50      0      1      0 |
  3. |  3       1     10      1      0      0 |
  4. |  4       .     50      0      0      1 |
  5. |  5       1     10      1      0      0 |
     +----------------------------------------+

Upvotes: 2

Nick Cox
Nick Cox

Reputation: 37358

Here's another way to do it:

bysort id (time): egen when_first_1 = min(cond(event == "1", time, .))
by id: gen tokeep = cond(when_first_1 == ., time == time[_N], time == when_first_1) 
keep if tokeep 
drop tokeep 

See especially Section 9 in this paper.

Upvotes: 2

Related Questions