私は仕事で大量の調査データなどを扱っており、行ごとにデータを処理するさまざまなスコアリングプログラムを作成しなければならないことがよくあります。たとえば、私は現在、心理測定機器からのサブスケールスコアを持つ12列を含むテーブルを扱っています。これらは、楽器の作成者によって提供されたテーブルを使用して正規化されたスコアに変換されます。これまでのところ簡単に思えます。
ただし、4つのテーブルがあります。楽器のスコアは、性別と年齢層によって異なります。したがって、たとえば、14歳の女性と10歳の男性は、異なる正規化テーブルを取得します。すべての正規化データはRデータフレームに保存されます。
私がやりたいのは、行に適用できる関数を作成することです。この関数は、正規化データからルックアップされたベクトルを返します。だから、漠然とこのようなもの:
converter <- function(rawscores,gender,age) {
if(gender=="Male") {
if(8 <= age & age <= 11) {convertvec <- c(1:12)}
if(12 <= age & age <= 14) {convertvec <- c(13:24)}
}
else if(gender=="Female") {
if(8 <= age & age <= 11) {convertvec <- c(25:36)}
if(12 <= age & age <= 14) {convertvec <- c(37:48)}
}
converted_scores <- rep(0,12)
for(z in 1:12) {
converted_scores[z] <- conversion_table[(unlist(rawscores)+1)[z],
convertvec[z]]
}
rm(z)
return(converted_scores)
}
編集済み:昨日実際に動作するようになったコードでこれを更新しました。このバージョンは、スコアを含む単純なベクトルを返します。これが私がそれをどのように実装したかです。
mydata[,21:32] <- 0
for(x in 1:dim(mydata)[1]) {
tscc_scores[x,21:32] <- converter(mydata[x,7:18],
mydata[x,"gender"],
mydata[x,"age"])
}
これは機能しますが、私が言ったように、それは悪い習慣であると理解するように与えられていますか?
補足:rawscores + 1の理由は、データフレームの最初のインデックスのスコアがゼロであるためです。
基本的に、この関数はそれほど複雑ではないように思われ、for(x in 1:number_of_records)を実行するループを使用して実装できることはわかっていますが、そうすることは不適切な方法であると理解しています。次のように、単にapply()を使用してこれを行うことを望んでいました。
apply(X=mydata[,1:12],MARGIN=1,
FUN=converter,gender=mydata[,"gender"],age=mydata[,"age"])
残念ながら、Rはこのアプローチを承認していないようです。これは、後続の引数に渡されるベクトルを反復処理せず、全体としてそれらを引数として受け取ろうとするためです。解決策はmapply()のように見えますが、列ではなく行に対してmapply()を使用する方法があるかどうかわかりません。
ですから、私の質問は3つあると思います。1つは、行に対してmapply()を使用する方法はありますか?2つ目は、apply()で引数を反復処理する方法はありますか?そして3つ、そこにもっと良いオプションはありますか?私はplyrパッケージについて多くのことを見聞きしましたが、Base Rに存在するオプションを完全に調査する前に、それに飛びつきたくありませんでした。