按每个键中的列对data.table进行排序

时间:2014-03-31 15:45:32

标签: r data.table

我有一个带有密钥xy的data.table,我想在每个密钥中按列z进行排序。

> DT
    x y          z
 1: a a  0.5526312
 2: a a  0.6339102
 3: a a -0.7490821
 4: a a -0.6850176
 5: a a  1.7943156
 6: a b  0.9271090
 7: a b  1.3936642
 8: a b  1.4815404
 9: a b -0.7850981
10: a b -1.0487700
11: b c  1.5184297
12: b c -0.4640705
13: b c -0.6513462
14: b c -0.5568319
15: b c  1.5422990
16: b d  0.8810654
17: b d -0.1895812
18: b d -2.6263378
19: b d  0.7371594
20: b d  1.4122076

我的第一次尝试是DT[order(z), .SD, by = list(x, y)],但是,这并未对键控列进行排序。我知道我可以分两步完成:

DT <- DT[order(x, y, z)]
setkeyv(DT, c('x', 'y'))

但是,这似乎不是一个好习惯,因为您希望在对键进行排序时,列z将保持排序状态。我也不想将z设置为关键,因为它以后不打算用作键。是否有更优雅的方式来实现这一目标?

2 个答案:

答案 0 :(得分:2)

为什么不:

setkey(DT, x, y, z)
setkey(DT, x, y)

使用setkey按所有三列排序,然后通过重置键从密钥中删除最后一列。此外,为了解决您对所维护的排序的担忧,请记录(data.table文档的详细信息部分的第2段):

  

排序稳定;即保留关系的顺序(如果有的话)。

这意味着当您按xy排序时, 后排序xy和{{1 }},任何z - z值集合中x的订单都不受干扰,因为它们都与y - x值相关联/ p>

答案 1 :(得分:1)

您可以设置包括z的键,然后取消设置。它仍然在x和y内按z排序,但它不再是键。

setkey(DT, x, y, z)
setkey(DT, x, y)