9

重複の可能性:
データ フレーム内の式を評価する R 関数を作成する方法

面倒な order() を使用する代わりに、data.frame を並べ替える関数を作成したいと考えています。次のようなものを考えると

> x=data.frame(a=c(5,6,7),b=c(3,5,1))
> x
  a b
1 5 3
2 6 5
3 7 1

私は次のようなことを言いたいです:

sort.df(x,b)

だからここに私の機能があります:

sort.df <- function(df, ...) {
  with(df, df[order(...),])
}

私はこれを本当に誇りに思っていました。R の遅延評価を考えると、... パラメータは必要な場合にのみ評価されると考えました。

「with」行を直接実行すると、機能します。しかし、機能はそうではありません。

> with(x,x[order(b),])
  a b
3 7 1
1 5 3
2 6 5
> sort.df(x,b)
Error in order(...) : object 'b' not found

何が問題で、どうすれば修正できますか? たとえば、plyr のようなパッケージでは、この種の「魔法」が頻繁に見られます。トリックは何ですか?

4

2 に答える 2

9

これはあなたが望むことをします:

sort.df <- function(df, ...) {
  dots <- as.list(substitute(list(...)))[-1]
  ord <- with(df, do.call(order, dots))
  df[ord,]
}

## Try it out
x <- data.frame(a=1:10, b=rep(1:2, length=10), c=rep(1:3, length=10))
sort.df(x, b, c)

そして、これもそうです:

sort.df2 <- function(df, ...) {
    cl <- substitute(list(...))
    cl[[1]] <- as.symbol("order")
    df[eval(cl, envir=df),]
}
 sort.df2(x, b, c)
于 2012-10-11T18:17:16.727 に答える
7

これは、b を渡すとき、実際にはオブジェクトを渡していないためです。関数の中にa を入れるbrowserと、私の言いたいことがわかるでしょう。どこかのインターネット ロボットからこれを盗みました。

x=data.frame(a=c(5,6,7),b=c(3,5,1))

sort.df <- function(df, ..., drop = TRUE){
    ord <- eval(substitute(order(...)), envir = df, enclos = parent.frame())
    return(df[ord, , drop = drop])
}

sort.df(x, b)

動作します。

応用的な意味でこれを行うための優れた方法を探している場合は、次のようになります。

library(taRifx)
sort(x, f=~b)
于 2012-10-11T18:17:18.163 に答える