裏 RjpWiki

Julia ときどき R, Python によるコンピュータプログラム,コンピュータ・サイエンス,統計学

分析プログラムにより結果が違う,そんな馬鹿な

2013年11月11日 | 統計学

Wikipedia の「主成分分析」に関するページ
http://ja.wikipedia.org/wiki/主成分分析 において。

主成分分析を実行するためのソフトウェアや関数によって、観測値の基準化の方法や数値計算のアルゴリズムに微細な差異が多く存在し、必ずしも全く同じ値が出るとは限らない(例えば、R における prcomp関数とFactoMineRのPCA関数の結果は異なる)。

とある。「全く同じ値」ということで,どの程度の違いを指しているのかはっきりしないが,これは,著者の誤解の可能性が大きい。

少なくとも,これを読んだ人が誤解してしまうことはあるようだ。別物を比較して違うといってもしようがない。以下に説明しよう。

--------------------------------------------------------------
1. FactoMineR の PCA は,デフォルトで変数を標準化する
     scale.unit
       a boolean, if TRUE (value set by default) then data
       are scaled to unit variance

   prcomp では,デフォルトでは変数を標準化しない。普通は,標準化すべきと述べられている。
     scale.    (最後のドットは引数名に含まれる)
       a logical value indicating whether the variables should
       be scaled to have unit variance before the analysis
       takes place. The default is FALSE for consistency with S,
       but in general scaling is advisable. Alternatively, a
       vector of length equal the number of columns of x can be
       supplied. The value is passed to scale.

2. FactoMineR の PCA が返すのは,負荷量(主成分と元の変数の相関係数にあたるもの)である。以下の 2 つであるが,同じものである。(- dimensions が何かは知らない)
     $var$coord       coord. for the variables           
     $var$cor         correlations variables - dimensions

> PCA(iris[1:4])$var$cor
                  Dim.1      Dim.2       Dim.3       Dim.4
Sepal.Length  0.8901688 0.36082989 -0.27565767 -0.03760602
Sepal.Width  -0.4601427 0.88271627  0.09361987  0.01777631
Petal.Length  0.9915552 0.02341519  0.05444699  0.11534978
Petal.Width   0.9649790 0.06399985  0.24298265 -0.07535950

   prcomp が返すものを print メソッドで書いて示されるものは,Rotation と名前が付けられている(要素名は $rotation)が,軸の回転はすなわち変数に対する重みということである。scale.=TRUE とした場合の結果は,もとの変数の相関係数行列の固有ベクトルそのものである。

> p = prcomp(iris[1:4], scale.=TRUE)
> p$rotation
                    PC1         PC2        PC3        PC4
Sepal.Length  0.5210659 -0.37741762  0.7195664  0.2612863
Sepal.Width  -0.2693474 -0.92329566 -0.2443818 -0.1235096
Petal.Length  0.5804131 -0.02449161 -0.1421264 -0.8014492
Petal.Width   0.5648565 -0.06694199 -0.6342727  0.5235971

> e = eigen(cor(iris[1:4]))
> e$vectors
           [,1]        [,2]       [,3]       [,4]
[1,]  0.5210659 -0.37741762  0.7195664  0.2612863
[2,] -0.2693474 -0.92329566 -0.2443818 -0.1235096
[3,]  0.5804131 -0.02449161 -0.1421264 -0.8014492
[4,]  0.5648565 -0.06694199 -0.6342727  0.5235971

prcomp の $rotation から負荷量を計算するのは以下のようにする。$sdev は,固有値の平方根(固有値は主成分の分散であり,その平方根をとると標準偏差 standardized deviation ということである)

> t(p$sdev*t(p$rotation))
                    PC1         PC2         PC3         PC4
Sepal.Length  0.8901688 -0.36082989  0.27565767  0.03760602
Sepal.Width  -0.4601427 -0.88271627 -0.09361987 -0.01777631
Petal.Length  0.9915552 -0.02341519 -0.05444699 -0.11534978
Petal.Width   0.9649790 -0.06399985 -0.24298265  0.07535950

ということで PCA の $var$cor と同じものが得られる。

がしかし,符号が違うじゃないかと思う人も多いようなのだが,主成分単位で絶対値は同じだが符号が異なるのは,符号を付け替えればよいだけなので,「結果が違う」わけではない。固有値の符号はコンピュータプログラムの違い(アルゴリズム,プログラムのコンパイラ,コンピュータアーキテクチャなど)で変わりうる。

3. 主成分得点の分散は,固有値に一致する(平均値は 0)。
   しかし,PCA の主成分得点($ind$coordは,分散(変動をサンプルサイズで割ったもの。すなわち不偏分散ではない)が固有値に一致する。
   prcomp の主成分得点は,不偏分散(変動を「サンプルサイズ-1」で割ったもの)が固有値に一致する。

> colSums(PCA(iris[1:4])$ind$coord^2)/150
     Dim.1      Dim.2      Dim.3      Dim.4
2.91849782 0.91403047 0.14675688 0.02071484

> colSums(prcomp(iris[1:4], scale.=TRUE)$x^2)/149
       PC1        PC2        PC3        PC4
2.91849782 0.91403047 0.14675688 0.02071484

ということなので,主成分得点の値は両者で若干異なる(が,変換可能である)。

コメント    この記事についてブログを書く
  • Twitterでシェアする
  • Facebookでシェアする
  • はてなブックマークに追加する
  • LINEでシェアする
« はじめダメなら,最後までダメ | トップ | ハートを描くプログラム »
最新の画像もっと見る

コメントを投稿

統計学」カテゴリの最新記事