web-dev-qa-db-ja.com

var()関数が計算された分散とは異なる答えを与えるのはなぜですか?

これがSOまたは他の.SEに入るかどうかはわかりませんでした。

ベクトルがあり、方程式を使用して「手で」分散を計算しようとしています(分散の定義に基づいていますが、Rで計算を実行しています)_V[X] = E[X^2] - E[X]^2_ where E[X] = sum (x * f(x))およびE[X^2] = sum (x^2 * f(x))

ただし、計算された分散は、Rが持っているvar()関数とは異なります(作業をチェックするために使用していました)。 var()関数が異なるのはなぜですか?分散の計算方法は?計算を数回確認したので、計算した値にかなり自信があります。私のコードは以下に提供されています。

_vec <- c(3, 5, 4, 3, 6, 7, 3, 6, 4, 6, 3, 4, 1, 3, 4, 4)
range(vec)
counts <- hist(vec + .01, breaks = 7)$counts
fx <- counts / (sum(counts)) #the pmf f(x)
x <- c(min(vec): max(vec)) #the values of x
exp <- sum(x * fx) ; exp #expected value of x
exp.square <- sum(x^2 * fx) #expected value of x^2
var <- exp.square - (exp)^2 ; var #calculated variance
var(vec)
_

これにより、計算された分散は2.234になりますが、var()関数は分散が2.383であると言います。

15
pocketlizard

V [X] = E [X ^ 2]-E [X] ^ 2は母集団の分散(ベクトル内の値が単なるサンプルではなく母集団全体である場合)であるのに対し、var関数は、母集団の分散について推定子を計算します(標本分散)。

10
Sven Hohenstein

これはすでに回答されていますが、人口分散とその見積もりサンプルから。これは例による可能性があります。

ベクトルvecが全母集団を表す場合、vecは単に分布関数を表す方法であり、それから導出したpmfでより簡潔に要約できます。重要なことに、この場合のvecの要素はランダム変数ではありません。この場合、pmfからのE [X]とvar [X]の計算は正しいです。

ただし、ほとんどの場合、データがある場合(たとえば、ベクトルの形式で)は、基礎となる母集団からのランダムサンプルです。ベクトルの各要素は、ランダム変数の観測値です。これは、母集団からの「引き分け」です。この例では、各要素が同じ分布(「iid」)から独立して描かれていると仮定するのが妥当です。実際には、このランダムサンプリングは、単なる偶然による変動があるため、真のpmfを計算できないことを意味します。同様に、サンプルからE [X]、E [X ^ 2]、したがってVar [X]の真の値を取得することはできません。これらの値は推定する必要があります。 サンプルの平均は、通常、E [X]の適切な推定値です(特に、不偏です)が、サンプル分散は、母分散のバイアス推定です。このバイアスを修正するには、係数n /(n-1)を乗算する必要があります。

この後者のケースは(教科書の演習を除いて)実際に最も見られるので、Rでvar()関数を呼び出すときに計算されます。したがって、「推定分散」を見つけるように求められた場合、ベクトルvecがランダムなサンプルであり、後者の場合に該当することを意味する可能性が最も高いです。これが元の質問である場合、あなたはあなたの答えを持っています、そして、変数の名前の選択とコード内のコメントが混乱につながる可能性があることが明らかになることを願っています:実際、ランダムなサンプルからpmf、期待値、または母集団の分散を計算することはできません:得ることができるのは、それらのestimates、およびそれらの1つ-分散のもの-は偏っています。

これを明確にしたかったのは、コーディングに見られるこの混乱は、これらの概念を初めて知ったときに非常に一般的だからです。特に、受け入れられた答えは誤解を招く可能性があります:V [X] = E [X ^ 2]-E [X] ^ 2はnotサンプルです分散;それは確かに人口分散であり、あなたはランダムなサンプルから得ることができません。この式の値をサンプルの推定値(平均値)で置き換えると、sample.V [X] = average [X ^ 2]-average [X] ^ 2が得られます。これはサンプルの分散、およびバイアスされています。

私はセマンティクスにこだわりがあると言う人もいます。ただし、受け入れられた回答の「表記法の乱用」は、誰もがそれを認識した場合にのみ受け入れられます。しかし、これらの概念的な違いを理解しようとする人にとっては、正確に保つことが最善だと思います。

6
wiwh

Statsパッケージのvar関数の出力に一致する「推定母集団分散」を計算する1つの方法を次に示します。

vec <- c(3, 5, 4, 3, 6, 7, 3, 6, 4, 6, 3, 4, 1, 3, 4, 4)
n <- length(vec)
average <- mean(vec)
differences <- vec - average
squared.differences <- differences^2
sum.of.squared.differences <-  sum(squared.differences)
estimator <- 1/(n - 1)
estimated.variance <- estimator * sum.of.squared.differences
estimated.variance
[1] 2.383333
var(vec) == estimated.variance # The "hand calculated" variance equals the variance in the stats package.
[1] TRUE

「推定器」という用語にラベルを付けることについて、人々はどう思うだろうか。

関数内(エラーや異常、statsパッケージ内のvar関数を処理する可能性は低い):

estimated.variance.by.hand <- function (x){
  n <- length(x)
  average <- mean(x)
  differences <- x - average
  squared.differences <- differences^2
  sum.of.squared.differences <-  sum(squared.differences)
  estimator <- 1/(n - 1)
  est.variance <- estimator * sum.of.squared.differences
  est.variance
}
estimated.variance.by.hand(vec)
estimated.variance.by.hand(1:10)
var(1:10)
estimated.variance.by.hand(1:100)
var(1:100)
1
dca

R-base var()は、分母でN-1を取り、より信頼性の高い(less biased)分散の推定量。幸いなことにvar()[〜#〜] n [〜#〜]を取るように指示するオプションがないため、その場合のために独自の分散関数を作成しました。

_var_N = function(x){var(x)*(length(x)-1)/length(x)}
_

そして、上記の関数、基本関数、手動の方法、@ dcaのestimated.variance.by.hand()関数を説明するコード:

_## Data
x = c(4,5,6,7,8,2,4,6,6)
mean_x = mean(x)


## Variance with N-1 in denominator
var(x)
sum((x - mean_x) ^2) / (length(x) - 1)
estimated.variance.by.hand(x)


## Variance with N in denominator
sum((x - mean_x) ^2) / length(x)
var(x) * (length(x) - 1) / length(x)
var_N = function(x){var(x)*(length(x)-1)/length(x)}
var_N(x)
_
1
SeGa