19

我有一个数据框 DF,其中一列是日期/时间,我想按此列的降序对数据框进行排序。

DF <- data.frame(ID=c('ID3', 'ID2','ID1'), end=c('4/1/10 12:00', '6/1/11 14:20', '1/1/09 11:10'), age=c(40,30,20));

我首先将end列转换为etusing et = as.POSIXct(DF$end,format='%m/%d/%Y %H:%M'),并使用以下内容,但得到参数不接受一元运算符'-'的错误:

out <- DF[order(-DF$et),];

我也尝试使用下降标志,但再次收到关于参数长度不同的错误。

out <- DF[order(DF$et, descending=TRUE),];

但是,升序似乎有效:out <- DF[order(DF$et),].

如何按降序排序(最近的时间在前)?谢谢你。

4

3 回答 3

16

对于您的问题,有一个简单而通用的解决方案,只需很少的代码。

正如您所注意到的,减号不适用于日期,因为负日期尚不存在!

但是,您可以使用通用函数获得相同的效果:rev()。因此,您将 rev 和 order 混合在一起,如下所示:

#init data
DF <- data.frame(ID=c('ID3', 'ID2','ID1'), end=c('4/1/10 12:00', '6/1/11 14:20', '1/1/09 11:10')
#change order
out <- DF[rev(order(as.Date(DF$end))),]

当您将减号与数字一起使用时,您将一次性对负数进行分类。我认为,当您使用 rev() 函数时,您将执行两次传递,一次按升序排序,另一次用于反转顺序。但在 3 次观察中,很难看到。

希望它有所帮助。

于 2014-06-15T09:56:50.693 回答
11

我认为这会起作用:

## Slightly bigger dataset with two times on same day:
DF <- data.frame(ID=c('ID3', 'ID2','ID1','ID4'), end=c('4/1/10 12:00', '6/1/11 14:20', '1/1/09 11:10' , '1/1/09 13:11'), age=c(40,30,20,20));

## Note to self - ALWAYS include a timezone.
DF$DTime <- as.POSIXct( DF$end , format = "%d/%m/%y %H:%M" , tz = "GMT")
DF[ order(DF$DTime , decreasing = TRUE ),]
#   ID          end age               DTime
#2 ID2 6/1/11 14:20  30 2011-01-06 14:20:00
#1 ID3 4/1/10 12:00  40 2010-01-04 12:00:00
#4 ID4 1/1/09 13:11  20 2009-01-01 13:11:00
#3 ID1 1/1/09 11:10  20 2009-01-01 11:10:00
于 2013-05-05T21:28:44.547 回答
0

使用dplyrlubridate-

library(dplyr)
library(lubridate)

DF %>% mutate(end = dmy_hm(end)) %>% arrange(desc(end))

#   ID                 end age
#1 ID2 2011-01-06 14:20:00  30
#2 ID3 2010-01-04 12:00:00  40
#3 ID1 2009-01-01 11:10:00  20

如果您不想更改end列的格式。

DF %>% arrange(desc(dmy_hm(end)))

#   ID          end age
#1 ID2 6/1/11 14:20  30
#2 ID3 4/1/10 12:00  40
#3 ID1 1/1/09 11:10  20
于 2021-06-26T03:09:13.683 回答