วิธีรับค่า p-pooled จากการทดสอบที่ทำในชุดข้อมูลหลายชุด


11

เมื่อใช้ Amelia ใน R ฉันได้รับชุดข้อมูลหลายชุด หลังจากนั้นฉันทำการทดสอบซ้ำใน SPSS ตอนนี้ฉันต้องการรวมผลการทดสอบ ฉันรู้ว่าฉันสามารถใช้กฎของ Rubin (ดำเนินการผ่านแพ็คเกจการใส่หลาย ๆ แบบใน R) เพื่อรวมหมายถึงและข้อผิดพลาดมาตรฐาน แต่ฉันจะรวมค่า p ได้อย่างไร เป็นไปได้ไหม? มีฟังก์ชั่นใน R ที่จะทำเช่นนั้น? ขอบคุณล่วงหน้า.


คุณอาจต้องการตรวจสอบข้อมูลเกี่ยวกับการวิเคราะห์อภิมาน p-value จุดเริ่มต้นที่ดีหนึ่งจุด: en.wikipedia.org/wiki/Fisher%27s_method
29889

คำตอบ:


13

ใช่เป็นไปได้และใช่มีRฟังก์ชั่นที่ทำ แทนการคำนวณค่า p ของการวิเคราะห์ซ้ำด้วยมือคุณสามารถใช้แพ็คเกจZeligซึ่งถูกอ้างถึงในบทความสั้น ๆของAmelia-package ( สำหรับวิธีการให้ข้อมูลเพิ่มเติมดูการอัพเดตด้านล่างของฉัน ) ฉันจะใช้ตัวอย่างจากAmelia-vignette เพื่อสาธิตสิ่งนี้:

library("Amelia")
data(freetrade)
amelia.out <- amelia(freetrade, m = 15, ts = "year", cs = "country")

library("Zelig")
zelig.fit <- zelig(tariff ~ pop + gdp.pc + year + polity, data = amelia.out$imputations, model = "ls", cite = FALSE)
summary(zelig.fit)

นี่คือเอาต์พุตที่สอดคล้องกันรวมถึง value:p

  Model: ls
  Number of multiply imputed data sets: 15 

Combined results:

Call:
lm(formula = formula, weights = weights, model = F, data = data)

Coefficients:
                Value Std. Error t-stat  p-value
(Intercept)  3.18e+03   7.22e+02   4.41 6.20e-05
pop          3.13e-08   5.59e-09   5.59 4.21e-08
gdp.pc      -2.11e-03   5.53e-04  -3.81 1.64e-04
year        -1.58e+00   3.63e-01  -4.37 7.11e-05
polity       5.52e-01   3.16e-01   1.75 8.41e-02

For combined results from datasets i to j, use summary(x, subset = i:j).
For separate results, use print(summary(x), subset = i:j).

zeligสามารถพอดีกับโฮสต์ของแบบจำลองอื่นนอกเหนือจากกำลังสองน้อยสุด

ในการรับช่วงความมั่นใจและระดับความเป็นอิสระสำหรับการประมาณการของคุณคุณสามารถใช้mitools:

library("mitools")
imp.data <- imputationList(amelia.out$imputations)
mitools.fit <- MIcombine(with(imp.data, lm(tariff ~ polity + pop + gdp.pc + year)))
mitools.res <- summary(mitools.fit)
mitools.res <- cbind(mitools.res, df = mitools.fit$df)
mitools.res

สิ่งนี้จะทำให้คุณมั่นใจในช่วงเวลาและสัดส่วนของความแปรปรวนทั้งหมดที่เกิดจากข้อมูลที่ขาดหายไป:

              results       se    (lower    upper) missInfo    df
(Intercept)  3.18e+03 7.22e+02  1.73e+03  4.63e+03     57 %  45.9
pop          3.13e-08 5.59e-09  2.03e-08  4.23e-08     19 % 392.1
gdp.pc      -2.11e-03 5.53e-04 -3.20e-03 -1.02e-03     21 % 329.4
year        -1.58e+00 3.63e-01 -2.31e+00 -8.54e-01     57 %  45.9
polity       5.52e-01 3.16e-01 -7.58e-02  1.18e+00     41 %  90.8

แน่นอนคุณสามารถรวมผลลัพธ์ที่น่าสนใจเป็นวัตถุเดียว:

combined.results <- merge(mitools.res, zelig.res$coefficients[, c("t-stat", "p-value")], by = "row.names", all.x = TRUE)

ปรับปรุง

หลังจากเล่นไปเรื่อย ๆ ฉันพบวิธีที่ยืดหยุ่นกว่าในการรับข้อมูลที่จำเป็นทั้งหมดโดยใช้mice-package เพื่อให้ใช้งานได้คุณจะต้องแก้ไขas.mids()ฟังก์ชันของแพ็คเกจ ใช้เวอร์ชันของ Gerko ที่โพสต์ในคำถามติดตามผลของฉัน:

as.mids2 <- function(data2, .imp=1, .id=2){
  ini <- mice(data2[data2[, .imp] == 0, -c(.imp, .id)], m = max(as.numeric(data2[, .imp])), maxit=0)
  names  <- names(ini$imp)
  if (!is.null(.id)){
    rownames(ini$data) <- data2[data2[, .imp] == 0, .id]
  }
  for (i in 1:length(names)){
    for(m in 1:(max(as.numeric(data2[, .imp])))){
      if(!is.null(ini$imp[[i]])){
        indic <- data2[, .imp] == m & is.na(data2[data2[, .imp]==0, names[i]])
        ini$imp[[names[i]]][m] <- data2[indic, names[i]]
      }
    } 
  }
  return(ini)
}

ด้วยการกำหนดไว้นี้คุณสามารถดำเนินการวิเคราะห์ชุดข้อมูลที่ถูกใส่ข้อมูลได้:

library("mice")
imp.data <- do.call("rbind", amelia.out$imputations)
imp.data <- rbind(freetrade, imp.data)
imp.data$.imp <- as.numeric(rep(c(0:15), each = nrow(freetrade)))
mice.data <- as.mids2(imp.data, .imp = ncol(imp.data), .id = NULL)

mice.fit <- with(mice.data, lm(tariff ~ polity + pop + gdp.pc + year))
mice.res <- summary(pool(mice.fit, method = "rubin1987"))

นี้จะให้ผลลัพธ์ทั้งหมดที่คุณได้รับใช้Zeligและmitoolsและอื่น ๆ :

                  est       se     t    df Pr(>|t|)     lo 95     hi 95 nmis   fmi lambda
(Intercept)  3.18e+03 7.22e+02  4.41  45.9 6.20e-05  1.73e+03  4.63e+03   NA 0.571  0.552
pop          3.13e-08 5.59e-09  5.59 392.1 4.21e-08  2.03e-08  4.23e-08    0 0.193  0.189
gdp.pc      -2.11e-03 5.53e-04 -3.81 329.4 1.64e-04 -3.20e-03 -1.02e-03    0 0.211  0.206
year        -1.58e+00 3.63e-01 -4.37  45.9 7.11e-05 -2.31e+00 -8.54e-01    0 0.570  0.552
polity       5.52e-01 3.16e-01  1.75  90.8 8.41e-02 -7.58e-02  1.18e+00    2 0.406  0.393

หมายเหตุการใช้pool()คุณยังสามารถคำนวณค่า -val ด้วยปรับสำหรับตัวอย่างขนาดเล็กได้โดยไม่ต้องระบุพารามิเตอร์ อะไรจะดีไปกว่านี้ตอนนี้คุณสามารถคำนวณและเปรียบเทียบโมเดลที่ซ้อนกันได้:d f R 2pdfmethodR2

pool.r.squared(mice.fit)

mice.fit2 <- with(mice.data, lm(tariff ~ polity + pop + gdp.pc))
pool.compare(mice.fit, mice.fit2, method = "Wald")$pvalue

1
mice.res <- summary(pool(mice.fit, method = "rubin1987"))คำตอบที่ดีก็แค่อยากจะชี้ให้เห็นการพิมพ์ผิดเล็กน้อยผมคิดว่าคุณหมายถึง:
FrankD

จับดี. ฉันแก้ไขคำผิด
crsh

8

โดยปกติคุณจะใช้ค่า p โดยใช้กฎรูบินของพารามิเตอร์ทางสถิติทั่วไปเช่นน้ำหนักการถดถอย ดังนั้นจึงไม่จำเป็นต้องรวมค่า p โดยตรง นอกจากนี้ยังสามารถรวบรวมสถิติอัตราส่วนความน่าจะเป็นเพื่อเปรียบเทียบแบบจำลอง ขั้นตอนการรวบรวมสำหรับสถิติอื่น ๆ สามารถพบได้ในหนังสือของฉันการใส่ข้อมูลที่มีความยืดหยุ่นของข้อมูลที่ขาดหายไปตอนที่ 6

ในกรณีที่ไม่มีการแจกแจงหรือวิธีการที่ทราบมีขั้นตอนที่ไม่ได้เผยแพร่โดย Licht และ Rubin สำหรับการทดสอบด้านเดียว ฉันใช้โพรซีเดอร์นี้เพื่อรวบรวมค่า p จากwilcoxon()โพรซีเดอร์ แต่มันเป็นเรื่องทั่วไปและตรงไปตรงมาเพื่อปรับให้เข้ากับการใช้งานอื่น ๆ

ใช้ขั้นตอนด้านล่างเฉพาะในกรณีที่ทุกอย่างล้มเหลวตอนนี้เรารู้เพียงเล็กน้อยเกี่ยวกับคุณสมบัติทางสถิติ

lichtrubin <- function(fit){
    ## pools the p-values of a one-sided test according to the Licht-Rubin method
    ## this method pools p-values in the z-score scale, and then transforms back 
    ## the result to the 0-1 scale
    ## Licht C, Rubin DB (2011) unpublished
    if (!is.mira(fit)) stop("Argument 'fit' is not an object of class 'mira'.")
    fitlist <- fit$analyses
        if (!inherits(fitlist[[1]], "htest")) stop("Object fit$analyses[[1]] is not an object of class 'htest'.")
    m <- length(fitlist)
    p <- rep(NA, length = m)
    for (i in 1:m) p[i] <- fitlist[[i]]$p.value
    z <- qnorm(p)  # transform to z-scale
    num <- mean(z)
    den <- sqrt(1 + var(z))
    pnorm( num / den) # average and transform back
}

@ Stef van Buuren คุณหมายถึงอะไรโดย 'ใช้ค่า p โดยใช้กฎรูบินของพารามิเตอร์ทางสถิติทั่วไปเช่นน้ำหนักการถดถอย' ไม่วิธีpool() การทำงานในแพคเกจของคุณ (ซึ่งเป็นที่ยอดเยี่ยมโดยวิธีการ) มาถึงที่ pooled p-value?
llewmills
โดยการใช้ไซต์ของเรา หมายความว่าคุณได้อ่านและทำความเข้าใจนโยบายคุกกี้และนโยบายความเป็นส่วนตัวของเราแล้ว
Licensed under cc by-sa 3.0 with attribution required.