10

ここで、myData が中央値より上か下かを示す新しい列を作成します

### MedianSplits based on Whole Data
#create some test data
myDataFrame=data.frame(myData=runif(15),myFactor=rep(c("A","B","C"),5)) 

#create column showing median split
myBreaks= quantile(myDataFrame$myData,c(0,.5,1))
myDataFrame$MedianSplitWholeData = cut(
    myDataFrame$myData,
    breaks=myBreaks, 
    include.lowest=TRUE,
    labels=c("Below","Above"))

#Check if it's correct
myDataFrame$AboveWholeMedian = myDataFrame$myData > median(myDataFrame$myData)
myDataFrame

正常に動作します。ここで、同じことを行いたいのですが、myFactor の各レベル内の分割の中央値を計算します。

私はこれを思いついた:

#Median splits within factor levels
byOutput=by(myDataFrame$myData,myDataFrame$myFactor, function (x) {
     myBreaks= quantile(x,c(0,.5,1))
     MedianSplitByGroup=cut(x,
       breaks=myBreaks, 
       include.lowest=TRUE,
       labels=c("Below","Above"))
     MedianSplitByGroup
     })

byOutput には、私が欲しいものが含まれています。因子 A、B、および C の各要素を正しく分類します。ただし、新しく計算された中央分割を示す新しい列 myDataFrame$FactorLevelMedianSplit を作成したいと思います。

「by」コマンドの出力を有用なデータフレーム列に変換するにはどうすればよいですか?

おそらく「by」コマンドは、これを行うRのような方法ではないと思います...

更新

factor() を巧みに使用する方法のティエリーの例と、スペクターの本で「ave」関数を発見したとき、追加のパッケージを必要としないこのソリューションを見つけました。

myDataFrame$MediansByFactor=ave(
    myDataFrame$myData,
    myDataFrame$myFactor,
    FUN=median)

myDataFrame$FactorLevelMedianSplit = factor(
    myDataFrame$myData>myDataFrame$MediansByFactor, 
    levels = c(TRUE, FALSE), 
    labels = c("Above", "Below"))
4

3 に答える 3

4

これは、plyr パッケージを使用したソリューションです。

myDataFrame <- data.frame(myData=runif(15),myFactor=rep(c("A","B","C"),5))
library(plyr)
ddply(myDataFrame, "myFactor", function(x){
    x$Median <- median(x$myData)
    x$FactorLevelMedianSplit <- factor(x$myData <= x$Median, levels = c(TRUE, FALSE), labels = c("Below", "Above"))
    x
})
于 2009-08-11T14:22:44.977 に答える
1

これはハックっぽい方法です。Hadley には、よりエレガントなものが付属している場合があります。

まず、by出力を単純に連結します。

 R> do.call(c,byOutput)
A1 A2 A3 A4 A5 B1 B2 B3 B4 B5 C1 C2 C3 C4 C5 
 1  2  2  1  1  1  1  2  1  2  1  2  1  1  2 

ここで因子レベル 1 と 2 を取得し、これらのレベルで新しい因子を再インデックス化するために使用できることが重要です。

R> c("Below","Above")[do.call(c,byOutput)]
 [1] "Below" "Above" "Above" "Below" "Below" "Below" "Below" "Above" 
 [8] "Below" "Above" "Below" "Above" "Below" "Below" "Above"
R> as.factor(c("Below","Above")[do.call(c,byOutput)])
[1] Below Above Above Below Below Below Below Above Below Above 
[11] Below Above Below Below Above
Levels: Above Below

data.frame次に、変更したい に割り当てることができます。

R> myDataFrame$FactorLevelMedianSplit <- 
      as.factor(c("Below","Above")[do.call(c,byOutput)])

更新: 新しい列を追加する前に、myDataFrame を再インデックスして AA ... AB ... BC ... C に並べ替える必要があります。演習として残しました...

于 2009-08-11T12:37:03.577 に答える