no <- rnorm(50)のようなデータでnoの値をarea毎に集計したいのですが,どのようにすればよいでしょうか。たとえば,areaごとの平均を求めて,各noの値から,対応するareaの合計値を引くということをしたいのです。
area <- rep(1:5,10)
ex <- data.frame(no,area)
for(i in 1:4){というようなことをやってみましたが,結果が出力されません。
selected <- is.element(ex$area,i)
mean(ex[selected,]$no)
}
No.05396 Re: Rで集計 【知ったかぶり】 2008/01/16(Wed) 15:08
> area.m <- by(ex$no,ex$area,mean)とか,
> area.m[[1]]
[1] 0.4721241> mean(subset(ex$no,area==1))とか,目的によっていろいろな方法があると思います.
[1] 0.4721241
後は下記をご参考に.
http://cse.naro.affrc.go.jp/takezawa/r-tips/r/44.html
No.05398 Re: Rで集計 【青木繁伸】 2008/01/16(Wed) 15:41
修正が一番少ない方法は,for の中の出力は明示的に print を使わないといけないということです。
ということで,
print(mean(ex[selected,]$no))
とすればよいでしょう。
さて,R の特徴を活かすためには,tapply やそのシュガーコートである by を使うとよいです。> tapply(no, area, mean)> areaごとの平均を求めて,各noの値から,対応するareaの合計値を引く
1 2 3 4 5
0.5945246 0.1323947 -0.0476108 0.4882766 -0.2697538
> by(no, area, mean)
INDICES: 1
[1] 0.5945246
-----------------------------------------------------------------
INDICES: 2
[1] 0.1323947
-----------------------------------------------------------------
INDICES: 3
[1] -0.0476108
-----------------------------------------------------------------
INDICES: 4
[1] 0.4882766
-----------------------------------------------------------------
INDICES: 5
[1] -0.2697538
データの順序が保存されませんが,以下のようにすることもできます> sapply(split(no, area), function(x) x-mean(x))
1 2 3 4 5
[1,] -0.008995784 0.5770713 -0.06169252 -0.94177377 0.8756413
[2,] -2.412480570 0.4977039 -0.22857331 -0.77243634 -0.6495682
[3,] -0.710772408 1.6849173 0.41823866 0.03193986 -0.4807782
[4,] 0.222375237 -1.0187522 -0.28396679 0.63243606 0.5684775
[5,] 0.185097322 1.3233904 -0.59671763 -2.04141400 -1.3279557
[6,] 1.210572917 -0.6140421 0.66799060 0.12384690 0.1074428
[7,] 0.217348576 2.0644389 2.09680114 1.14416904 0.5240250
[8,] -0.103336323 -0.4564813 -1.61443945 1.27945725 0.2955549
[9,] 0.533986231 -2.5127528 -1.01265475 0.44886394 1.1242055
[10,] 0.866204801 -1.5454935 0.61501405 0.09491106 -1.0370450
No.05401 Re: Rで集計 【Rはじめました】 2008/01/16(Wed) 16:53
知ったかぶり様,青木先生,早速ありがとうございました。
byという便利な関数があるのですね。知りませんでした。
また,試していた方法でも,
print(mean(ex[selected,]$no))
をつけるだけで解決しました。
と ころで,最後のデータの順序が保存されないというのは,どういうことなのでしょうか。ちょっとよくわかりません。各行の中の横に並んでいる数値は対応して いるけれども,[1,][2,][3,]....[10,]の順番は実行するたびに変わってしまうということでしょうか。
No.05402 Re: Rで集計 【青木繁伸】 2008/01/16(Wed) 17:00
与えられたデータでは,area は 1,2,3,4,5,1,2,3,4,5 となっていますが,split(no, area) は area が 1 のものの no から mean(no) をひいて,area が 2 のものの no から。。。とやって,その結果を行列として与えます。R の行列は列優先なので,結果の第1列が area=1 の結果,です。今の場合はこの行列を行優先で読めば望む結果になってはいるのですが,area がランダムになっているとデータ順が保存されないのはちょっと困るでしょうね。
で,そう言うときのためには以下のように> no-tapply(no, area, mean)[area]こ れだと,データの順は保存されています。この例では,area を添え字に使っているので,area が数値でない場合にはもう一工夫が必要になります。また,もし area が整数であっても,1から始まる連続する整数を採らない場合(たとえば1がない場合)や途中が抜けているときなどにもエラーが発生します。どんな場合にも うまく動くやり方を考えるのは,なかなか大変なこともあります。
1 2 3 4 5 1
-0.008995784 0.577071324 -0.061692517 -0.941773770 0.875641277 -2.412480570
2 3 4 5 1 2
0.497703857 -0.228573307 -0.772436340 -0.649568182 -0.710772408 1.684917350
途中省略
4 5
0.094911057 -1.037045013
No.05403 Re: Rで集計 【Rはじめました】 2008/01/16(Wed) 17:18
なるほど,ありがとうございます。
次のようにすると,最初に与えられたデータに対応させて表示できるのですね。A <- no-tapply(no, area, mean)[area]大変助かりました。
data.frame(no,area,A)
No.05404 Re: Rで集計 【takahashi】 2008/01/16(Wed) 18:52
こういうのもありです。ex$res<-resid(lm(no~factor(area)-1,ex))実際,解析中によく使います。
No.05405 Re: Rで集計 【青木繁伸】 2008/01/16(Wed) 19:01
なるほど,No.5404 ならば area が何であろうと望む結果になりますね
No.05412 Re: Rで集計 【Rはじめました】 2008/01/17(Thu) 08:53
takahashi様ありがとうございます。
> こういうのもありです。
> ex$res<-resid(lm(no~factor(area)-1,ex))
noをareaで回帰した直線に対するnoの残差ということになるようですが,-1の意味するところを教えて頂けないでしょうか。
No.05413 Re: Rで集計 【青木繁伸】 2008/01/17(Thu) 09:31
「定数項を含めない」重回帰ということを指示するものです
実質的には,定数項はfactorの最初のカテゴリーに振り分けられ,その他のカテゴリーの回帰係数に調整が加えられます
定数項を含める含めないにかかわらず,今回の場合には同じ答えになります。> all.equal(resid(lm(no~factor(area)-1,ex)), resid(lm(no~factor(area),ex)))
[1] TRUE
No.05414 Re: Rで集計 【Rはじめました】 2008/01/17(Thu) 10:01
青木先生,重ね重ねありがとうございました。
● 「統計学関連なんでもあり」の過去ログ--- 041 の目次へジャンプ
● 「統計学関連なんでもあり」の目次へジャンプ
● 直前のページへ戻る