Ответ @Ronald 's является лучшим и широко применим ко многим подобным проблемам (например, есть ли статистически значимая разница между мужчинами и женщинами в отношениях между весом и возрастом?). Тем не менее, я добавлю другое решение, которое, хотя и не так количественно (оно не обеспечивает p- значение), дает хорошее графическое отображение разницы.
РЕДАКТИРОВАТЬ : в соответствии с этим вопросом , похоже predict.lm
, что функция, используемая ggplot2
для вычисления доверительных интервалов, не вычисляет одновременные доверительные полосы вокруг кривой регрессии, а только точечные доверительные полосы. Эти последние полосы не являются правильными для оценки того, являются ли две подобранные линейные модели статистически различными или, по-другому, могут ли они быть совместимы с одной и той же истинной моделью или нет. Таким образом, они не являются правильными кривыми, чтобы ответить на ваш вопрос. Поскольку, по-видимому, нет встроенной функции R для получения одновременных доверительных интервалов (странно!), Я написал свою собственную функцию. Вот:
simultaneous_CBs <- function(linear_model, newdata, level = 0.95){
# Working-Hotelling 1 – α confidence bands for the model linear_model
# at points newdata with α = 1 - level
# summary of regression model
lm_summary <- summary(linear_model)
# degrees of freedom
p <- lm_summary$df[1]
# residual degrees of freedom
nmp <-lm_summary$df[2]
# F-distribution
Fvalue <- qf(level,p,nmp)
# multiplier
W <- sqrt(p*Fvalue)
# confidence intervals for the mean response at the new points
CI <- predict(linear_model, newdata, se.fit = TRUE, interval = "confidence",
level = level)
# mean value at new points
Y_h <- CI$fit[,1]
# Working-Hotelling 1 – α confidence bands
LB <- Y_h - W*CI$se.fit
UB <- Y_h + W*CI$se.fit
sim_CB <- data.frame(LowerBound = LB, Mean = Y_h, UpperBound = UB)
}
library(dplyr)
# sample datasets
setosa <- iris %>% filter(Species == "setosa") %>% select(Sepal.Length, Sepal.Width, Species)
virginica <- iris %>% filter(Species == "virginica") %>% select(Sepal.Length, Sepal.Width, Species)
# compute simultaneous confidence bands
# 1. compute linear models
Model <- as.formula(Sepal.Width ~ poly(Sepal.Length,2))
fit1 <- lm(Model, data = setosa)
fit2 <- lm(Model, data = virginica)
# 2. compute new prediction points
npoints <- 100
newdata1 <- with(setosa, data.frame(Sepal.Length =
seq(min(Sepal.Length), max(Sepal.Length), len = npoints )))
newdata2 <- with(virginica, data.frame(Sepal.Length =
seq(min(Sepal.Length), max(Sepal.Length), len = npoints)))
# 3. simultaneous confidence bands
mylevel = 0.95
cc1 <- simultaneous_CBs(fit1, newdata1, level = mylevel)
cc1 <- cc1 %>% mutate(Species = "setosa", Sepal.Length = newdata1$Sepal.Length)
cc2 <- simultaneous_CBs(fit2, newdata2, level = mylevel)
cc2 <- cc2 %>% mutate(Species = "virginica", Sepal.Length = newdata2$Sepal.Length)
# combine datasets
mydata <- rbind(setosa, virginica)
mycc <- rbind(cc1, cc2)
mycc <- mycc %>% rename(Sepal.Width = Mean)
# plot both simultaneous confidence bands and pointwise confidence
# bands, to show the difference
library(ggplot2)
# prepare a plot using dataframe mydata, mapping sepal Length to x,
# sepal width to y, and grouping the data by species
p <- ggplot(data = mydata, aes(x = Sepal.Length, y = Sepal.Width, color = Species)) +
# add data points
geom_point() +
# add quadratic regression with orthogonal polynomials and 95% pointwise
# confidence intervals
geom_smooth(method ="lm", formula = y ~ poly(x,2)) +
# add 95% simultaneous confidence bands
geom_ribbon(data = mycc, aes(x = Sepal.Length, color = NULL, fill = Species, ymin = LowerBound, ymax = UpperBound),alpha = 0.5)
print(p)
Внутренние полосы - это те, которые рассчитываются по умолчанию geom_smooth
: это точечные 95% доверительные полосы вокруг кривых регрессии. Внешние, полупрозрачные полосы (спасибо за графический совет, @Roland) вместо этого представляют собой одновременные 95% доверительные полосы. Как вы можете видеть, они больше, чем точечные полосы, как и ожидалось. Тот факт, что одновременные доверительные интервалы на двух кривых не перекрываются, можно считать показателем того, что различие между двумя моделями является статистически значимым.
Конечно, для проверки гипотезы с действительным p-значением следует придерживаться подхода @Roland, но этот графический подход можно рассматривать как анализ поисковых данных. Также сюжет может дать нам дополнительные идеи. Понятно, что модели для двух наборов данных статистически различны. Но похоже, что две модели степени 1 будут соответствовать данным почти так же хорошо, как две квадратичные модели. Мы можем легко проверить эту гипотезу:
fit_deg1 <- lm(data = mydata, Sepal.Width ~ Species*poly(Sepal.Length,1))
fit_deg2 <- lm(data = mydata, Sepal.Width ~ Species*poly(Sepal.Length,2))
anova(fit_deg1, fit_deg2)
# Analysis of Variance Table
# Model 1: Sepal.Width ~ Species * poly(Sepal.Length, 1)
# Model 2: Sepal.Width ~ Species * poly(Sepal.Length, 2)
# Res.Df RSS Df Sum of Sq F Pr(>F)
# 1 96 7.1895
# 2 94 7.1143 2 0.075221 0.4969 0.61
Разница между моделью степени 1 и моделью степени 2 незначительна, поэтому мы также можем использовать две линейные регрессии для каждого набора данных.