Reputation: 305
I have a few thousand cases and need to replace the order with a collapsed version for each id variable. The have column is what I'm working with and the want column is what I want it to look like. Any thoughts would be much appreciated.
id<-c(1,1,1,2,2,3,3,3,3,4,4,4,4,4)
have<-c(0,1,3,0,2,0,1,4,6,1,3,4,5,7)
want<-c(0,1,2,0,1,0,1,2,3,0,1,2,3,4)
reorder<-cbind(id,have,want)
reorder
id have want
[1,] 1 0 0
[2,] 1 1 1
[3,] 1 3 2
[4,] 2 0 0
[5,] 2 2 1
[6,] 3 0 0
[7,] 3 1 1
[8,] 3 4 2
[9,] 3 6 3
[10,] 4 1 0
[11,] 4 3 1
[12,] 4 4 2
[13,] 4 5 3
[14,] 4 7 4
Upvotes: 1
Views: 745
Reputation: 24945
You could use dplyr, and give the rownumber - 1 to each:
library(dplyr)
as.data.frame(reorder) %>% group_by(id) %>%
mutate(want2 = row_number() - 1)
Source: local data frame [14 x 4]
Groups: id [4]
id have want want2
(dbl) (dbl) (dbl) (dbl)
1 1 0 0 0
2 1 1 1 1
3 1 3 2 2
4 2 0 0 0
5 2 2 1 1
6 3 0 0 0
7 3 1 1 1
8 3 4 2 2
9 3 6 3 3
10 4 1 0 0
11 4 3 1 1
12 4 4 2 2
13 4 5 3 3
14 4 7 4 4
Upvotes: 2
Reputation: 92282
All you trying to do is to rank by group it seems. Here's a simple attempt
ave(have, id, FUN = rank) - 1L
## [1] 0 1 2 0 1 0 1 2 3 0 1 2 3 4
You may want to look into ?rank
for different variations of duplicates handling (ties.method
in particular)
Upvotes: 4