swhusky
swhusky

Reputation: 305

Relevel and reorder factors in R

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

Answers (2)

jeremycg
jeremycg

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

David Arenburg
David Arenburg

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

Related Questions