简体   繁体   English

R 和 Python 之间加权 t 检验的不同结果

[英]Different results with weighted t test between R and Python

I'm running a weighted t test in Python and am seeing different results.我正在 Python 中运行加权 t 测试,但看到了不同的结果。 It appears that the issue is the degree of freedom calculation.看来问题是自由度计算。 Would like to understand why I'm seeing different outputs.想了解为什么我看到不同的输出。

Here is some sample code.这是一些示例代码。

In R:在 R 中:

library(weights)
x <- c(373,398,245,272,238,241,134,410,158,125,198,252,577,272,208,260)
y <- c(411,471,320,364,311,390,163,424,228,144,246,371,680,384,279,303)

weightsa = c(rep(1,8), rep(2,8))
weightsb = c(rep(2,8), rep(1,8))

wtd.t.test(x = x,
           y = y,
           weight = weightsa,
           weighty = weightsb, samedata=F)

$test [1] "Two Sample Weighted T-Test (Welch)"

$coefficients
    t.value          df     p.value 
-1.88907197 29.93637837  0.06860382 

$additional Difference     Mean.x     Mean.y   Std. Err   -80.50000 
267.12500  347.62500   42.61352

In Python:在 Python 中:

import numpy as np
from statsmodels.stats.weightstats import ttest_ind
x = np.asarray([373,398,245,272,238,241,134,410,158,125,198,252,577,272,208,260])
y = np.asarray([411,471,320,364,311,390,163,424,228,144,246,371,680,384,279,303])

weightsa = [1] * 8 + [2] * 8
weightsb = [2] * 8 + [1] * 8

ttest_ind(x, y, usevar='unequal', weights=(weightsa, weightsb))

(-2.3391969704691085, 0.023733058922455107, 45.90244683439944)

P value is .06 in R, .02 in Python. R 中的 P 值为 .06,Python 中为 .02。
The R source code uses the Satterthwaite formula for degrees of freedom: R 源代码使用 Satterthwaite 公式计算自由度:

df <- (((vx/n) + (vy/n2))^2)/((((vx/n)^2)/(n - 1)) + 
      ((vy/n2)^2/(n2 - 1)))

The Python function source code also purports to use this formula: Python 函数源代码也声称使用此公式:

def dof_satt(self):
        '''degrees of freedom of Satterthwaite for unequal variance
        '''
        d1 = self.d1
        d2 = self.d2
        #this follows blindly the SPSS manual
        #except I use  ``_var`` which has ddof=0
        sem1 = d1._var / (d1.nobs-1)
        sem2 = d2._var / (d2.nobs-1)
        semsum = sem1 + sem2
        z1 = (sem1 / semsum)**2 / (d1.nobs - 1)
        z2 = (sem2 / semsum)**2 / (d2.nobs - 1)
        dof = 1. / (z1 + z2)
        return dof

The numerator here looks the same but the denominator appears quite different.这里的分子看起来一样,但分母却大不相同。

The problem you had here is that weights::wtd.t.test() has a (to me, strange) default argument mean1 = TRUE , which governs "whether the weights should be forced to have an average value of 1" (from help("wtd.t.test") ).你在这里遇到的问题是weights::wtd.t.test()有一个(对我来说很奇怪)默认参数mean1 = TRUE ,它控制“是否应该强制权重为 1”(来自help("wtd.t.test") )。

If we use mean1 = FALSE , we get the same behavior as ttest_ind() :如果我们使用mean1 = FALSE ,我们会得到与ttest_ind()相同的行为:

wtd.t.test(x = x,
           y = y,
           weight = weightsa,
           weighty = weightsb,
           samedata = FALSE,
           mean1 = FALSE)

$test
[1] "Two Sample Weighted T-Test (Welch)"

$coefficients
    t.value          df     p.value 
-2.33919697 45.90244683  0.02373306 

$additional
Difference     Mean.x     Mean.y   Std. Err 
 -80.50000  267.12500  347.62500   34.41352 

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM