将数据框中的行相应地移动到一列

时间:2016-07-28 18:54:08

标签: r dataframe move

我希望在我的数据框中移动特定的行,相应地移动到一列。

df <- read.table(text = 'ID Day Count
33012   9526    4
35004   9526    4
37006   9526    4
37008   9526    4
21009   1913    3
24005   1913    3
25009   1913    3
29002   12551   2
30001   12551   2
25009   14329   1
48007   9525    0
49002   1912    0
51003   12550   0
56001   12550   0', header = TRUE)

鉴于上述数据帧,我想将Count列中的0行相应地移动到Day列,即9526之后的9525,1913之后的1912,12551之后的12550。

输出应为:

ID       Day  Count
33012   9526    4
35004   9526    4
37006   9526    4
37008   9526    4
48007   9525    0
21009   1913    3
24005   1913    3
25009   1913    3
49002   1912    0
29002   12551   2
30001   12551   2
51003   12550   0
56001   12550   0
25009   14329   1

请忽略ID列。

与此主题相关的新问题:

Move rows in a dataframe accordingly to one column (2)

1 个答案:

答案 0 :(得分:1)

回答更新的问题

我认为我找到了一个非常酷的解决方案来解决您的更新问题:

df[order(match(df$Day+(z <- df$Count==0L),unique(df$Day[!z])),z),];
##       ID   Day Count
## 1  33012  9526     4
## 2  35004  9526     4
## 3  37006  9526     4
## 4  37008  9526     4
## 11 48007  9525     0
## 5  21009  1913     3
## 6  24005  1913     3
## 7  25009  1913     3
## 12 49002  1912     0
## 8  29002 12551     2
## 9  30001 12551     2
## 13 51003 12550     0
## 14 56001 12550     0
## 10 25009 14329     1

此解决方案有两个方面:

1:首先,它按“规范”Day值排序。对于非零Day行,规范df$Day值为Count,对于零df$Day+1L行,Count值为Day。这是通过将规范Day值匹配到非零Count行的唯一规范Day值的向量中来实现的,这些值还用于保留规范{{的传入顺序1}}值。规范Day值使用逻辑加法计算,将FALSE视为零,将TRUE视为一。零/非零区分在运行中在局部变量z中捕获,从而免除了对该信息的后续冗余计算的需要。

2:其次,它在零Count行之前命令非零Count行。由于z已在行中先前计算过,因此我们可以将其作为第二个参数传递给order()来执行此操作。按逻辑向量排序时,FALSE会在TRUE之前排序,因此可以直接使用。

回答原始问题

我认为这就是你要找的东西:

df$vl <- ave(df$vl,df$id,FUN=function(x) sort(decreasing=T,x));
df;
##    id vl
## 1   C  5
## 2   C  3
## 3   C  2
## 4   C  2
## 5   A  5
## 6   A  5
## 7   A  4
## 8   A  2
## 9   B  4
## 10  B  2
## 11  B  1
## 12  B  1

上述内容对每个vl群组中的id列进行排序,与其他id群组无关。

数据

set.seed(1L);
df <- data.frame(id=rep(c('C','A','B'),each=4L),vl=sample(5L,12L,T));

您的问题的另一种解释是,您希望按vl列对整个data.frame进行排序,但在vl的每个唯一值中,您希望更喜欢该唯一值的顺序id列中的值出现在原始data.frame中(尽管并非所有id值都与每个唯一vl值一起表示)。以下是如何做到的:

df[order(-df$vl,match(df$id,unique(df$id))),];
##    id vl
## 1   C  5
## 5   A  5
## 6   A  5
## 7   A  4
## 9   B  4
## 2   C  3
## 3   C  2
## 4   C  2
## 8   A  2
## 10  B  2
## 11  B  1
## 12  B  1