1. ホーム
  2. r

[解決済み] 大きなデータフレームを、カラムの共通値に基づいてデータフレームのリストに分割する。

2023-01-03 06:34:27

質問

10列のデータフレームがあり、quot;users" のアクションを収集しています。私は、単一のアクターのアクションを分離するために、"user" 識別子を含む列で分割された個々のデータフレームを抽出しようとしています(データフレームのリストまたはベクトルを取得する)。

ID | Data1 | Data2 | ... | UserID
1  | aaa   | bbb   | ... | u_001
2  | aab   | bb2   | ... | u_001
3  | aac   | bb3   | ... | u_001
4  | aad   | bb4   | ... | u_002

になります。

list(
ID | Data1 | Data2 | ... | UserID
1  | aaa   | bbb   | ... | u_001
2  | aab   | bb2   | ... | u_001
3  | aac   | bb3   | ... | u_001
,
4  | aad   | bb4   | ... | u_002
...)

小さなサンプル(1000行)では、次のようにすると非常によく動作します。

paths = by(smallsampleMat, smallsampleMat[,"userID"], function(x) x)

という具合に、例えばpath[1]で欲しい要素にアクセスします。

オリジナルの大きなデータフレーム、あるいは行列表現に適用すると、これは私のマシン(4GB RAM、MacOSX 10.6、R 2.15)を窒息させ、決して完了しません(新しいRバージョンが存在することは知っていますが、これは主な問題ではないと信じています)。

分割はより高性能で、長い時間の後に完了するようですが、私は(劣ったRの知識)結果のベクトルのリストを行列のベクトルに分割する方法を知りません。

path = split(smallsampleMat, smallsampleMat[,10]) 

を使うことも検討しました。 big.matrix などを使用することも考えましたが、あまり成功せず、処理を高速化することはできませんでした。

どのように解決するのですか?

リスト内の各要素にアクセスするには、例えば path[[1]] . 行列のセットをアトミックベクターに入れ、各要素にアクセスすることはできません。行列は次元属性を持つ原子ベクトルです.私なら、リスト構造体を返す split そのために設計されたのです。各リスト要素は異なる型とサイズのデータを保持することができるので、非常に汎用性があり、あなたは *apply 関数を使って、リストの各要素をさらに操作することができます。以下はその例です。

#  For reproducibile data
set.seed(1)

#  Make some data
userid <- rep(1:2,times=4)
data1 <- replicate(8 , paste( sample(letters , 3 ) , collapse = "" ) )
data2 <- sample(10,8)
df <- data.frame( userid , data1 , data2 )

#  Split on userid
out <- split( df , f = df$userid )
#$`1`
#  userid data1 data2
#1      1   gjn     3
#3      1   yqp     1
#5      1   rjs     6
#7      1   jtw     5

#$`2`
#  userid data1 data2
#2      2   xfv     4
#4      2   bfe    10
#6      2   mrx     2
#8      2   fqd     9

各要素へのアクセスは [[ 演算子を使ってアクセスします。

out[[1]]
#  userid data1 data2
#1      1   gjn     3
#3      1   yqp     1
#5      1   rjs     6
#7      1   jtw     5

あるいは *apply 関数を使用して、各リストの要素に対してさらに操作を行うこともできます。例えば、リストの要素の平均を取るには data2 列の平均を取るには、次のようにsapplyを使うことができます。

sapply( out , function(x) mean( x$data2 ) )
#   1    2 
#3.75 6.25