为什么在传入子集数据帧时 R 中的 order() 会生成 NA?

Why does order() in R generate NAs when passing in a subsetted dataframe?

在理解这里发生的事情时遇到了一些困难,在我看来,这两种对下面的数据框进行排序的方法是等效的。

我们的数据框,

cols <- c("chr","id","value")
df <-   data.frame(c(1:5),c("ENSG1","ENSG2","ENSG3","ENSG4","ENSG5"),runif(5,5.0,10.0))
names(df) <- cols
df <- df[sample(nrow(df)),]
df

chr    id    value
5      ENSG5 8.913645
2      ENSG2 6.117744
4      ENSG4 8.558403
3      ENSG3 9.625546
1      ENSG1 6.105577

现在,方法 1:

df[order(df[,c("chr","id")]),]

chr    id    value
1      ENSG1 6.105577
2      ENSG2 6.117744
3      ENSG3 9.625546
4      ENSG4 8.558403
5      ENSG5 8.913645
NA    <NA>       NA
NA    <NA>       NA
NA    <NA>       NA
NA    <NA>       NA
NA    <NA>       NA

出于某种奇怪的原因抛出 NA,同时将 df 列传递给 order(),如

方法二:

df[order(df$chr,df$id),]

chr    id    value
1      ENSG1 6.105577
2      ENSG2 6.117744
3      ENSG3 9.625546
4      ENSG4 8.558403
5      ENSG5 8.913645

或者没有。

谁能解释一下为什么方法 1 和方法 2 不能互换?

当我们查看 ?order 时,它的第一个参数记录为:

a sequence of numeric, complex, character or logical vectors, all of the same length, or a classed R object.

没有任何迹象表明它适用于数据框。 "classed R object" 有点含糊,表明数据框不会抛出错误,但肯定不会说 "or a data frame".

描述说:

See the examples for how to use these functions to sort data frames, etc.

当你调用order或数据框时,你可以看到发生了什么:

order(data.frame(a = 1:5, b = 5:1))
# [1]  1 10  2  9  3  8  4  7  5  6

看起来它把数据框强制转换为一个向量,并对其进行排序。一般不是很有用。这就是为什么当你 运行 df[order(df[,c("chr","id")]),] 时你会得到 NA 行。您的输入数据框有 2 列,因此 order() 输出的行数是数据框的两倍。

您已经找到了排序数据框的正确方法,即将实际向量提供给 order。向量可以是数据框的单独列,也可以是其他长度正确的向量。