404 Not Found

404 Not Found


nginx

R 線形回帰:lm() の完全ガイド

これまでの3回のレッスンでは、記述統計、確率分布、仮説検定について学びました。これらはすべて「データを分析する」ことに関わっています。今回のレッスンでは、「データを使って未来を予測する」こと、つまり線形回帰へと進みます。これがRの真の「見どころ」です。「1,000,000の投資で5,000,000の売上を生み出す」という広告の主張は、信頼できるものでしょうか? lm() を使って、たった1行で計算してみましょう。

このレッスンを修了すると、R を使用して線形回帰の分析、予測、係数の解釈、有意性検定、モデルの診断を行うことができるようになります。これらは、データサイエンス業務の 80% を占めています。

1. 学習内容



2. 売上予測に関する話

(1) 課題:広告と営業

ボブは、「広告費」が「売上」に与える影響を予測したいと考えています:

R
Advertising expenses(0K)   Sales(0K)
1            3
2            5
3            7
4            9
5            12

「広告に10,000を費やせば、20,000の売り上げが見込める」というのは「単なる直感」でしょうか? LMを使って正確に計算してみましょう――

(2) Rを用いた解決策

R
# 1. Model Building in One Line
model <- lm(sales ~ ad, data = df)

# 2. View the results in one line
summary(model)
# Coefficients:
#             Estimate Std. Error t value Pr(>|t|)    
# (Intercept)   1.0000     0.3536   2.828   0.0474 *  
# ad            2.0000     0.1054  18.975 0.0001 ***
# ---
# Residual standard error: 0.3651
# Multiple R-squared:  0.9923

# 3. One-Line Forecast
predict(model, data.frame(ad = 10))
# [1] 21  ← invest $10,000Advertising Sales Forecast 210,000

3行のコード → モデル + 予測



3. 線形回帰の原理

(1) 数式

R
Y = β₀ + β₁X + ε
   │   │    │
   │   │    └─ Error term (Residual)
   │   └────── Slope (X increases by 1, Y changes by how much?)
   └────────── Intercept (Y value when X=0)
100%
graph LR
    A[Actual data points] --> B[Linear Model Fitting]
    B --> C[Find the Best Straight Line]
    C --> D[Minimize the sum of squared residuals]
    D --> E[Least Squares Method OLS]
    
    style A fill:#cce5ff
    style B fill:#d4edda
    style C fill:#fff3cd
    style D fill:#f8d7da
    style E fill:#e1d4ff

(2) 核心となる考え方

すべての点からその直線までの「距離の二乗和」が最小となる直線を求める(普通最小二乗法、OLS)。



4. lm() の基本的な使い方

(1) 数式の構文の4つの種類

R
# 1. y ~ x (Most Commonly Used)
lm(sales ~ ad, data = df)

# 2. y ~ x1 + x2 (Multiple)
lm(sales ~ ad + price, data = df)

# 3. y ~ x1 * x2 (Interaction)
lm(sales ~ ad * price, data = df)

# 4. y ~ . (All other variables)
lm(sales ~ ., data = df)

(2) 最初の回帰分析

R
# Data
df <- data.frame(
  ad = c(1, 2, 3, 4, 5, 6, 7, 8, 9, 10),
  sales = c(3, 5, 7, 9, 12, 13, 15, 17, 19, 21)
)

# Build a model
model <- lm(sales ~ ad, data = df)

# Abstract
summary(model)

出力の詳細な説明:

R
Call:
lm(formula = sales ~ ad, data = df)

Residuals:
   Min     1Q  Median     3Q     Max 
-0.4    -0.3     0.0     0.3     0.4 

Coefficients:
            Estimate Std. Error t value Pr(>|t|)    
(Intercept)   1.0000     0.2041   4.899  0.00106 ** 
ad            2.0000     0.0340  58.787 1.01e-12 ***
---
Signif. codes:  0 ‘*’ 0.001 ‘’ 0.01 ‘*’ 0.05 ‘.’ 0.1 ‘ ’ 1

Residual standard error: 0.3651 on 8 degrees of freedom
Multiple R-squared:  0.9977,	Adjusted R-squared:  0.9974
F-statistic: 3456 on 1 and 8 DF,  p-value: 1.008e-12

(3) 6つの主要指標の分析

項目 意味 説明
推定値 係数の推定値 ad=2.0 は、広告費が 10,000 増加すると、売上が 20,000 増加することを示す
標準誤差 係数の標準誤差 係数推定値の精度(数値が小さいほど良い)
t値 t統計量 推定値/標準誤差
Pr(>|t|) p値 係数が 有意でない(0) である確率
決定係数 モデルによって説明される分散の割合(0~1)
F統計量 F統計量 全体モデルの有意性
💡 重要なポイント:p値が0.05未満である場合、その係数は「0と有意に異なる」ことを示しており、つまりこの変数はYに有意な影響を与えているということです。



5. predict() の予測

(1) 基本予測

R
# Single-Point Forecast
predict(model, data.frame(ad = 10))
# [1] 21  ← invest $10,000Advertising Sales Forecast 210,000

# Multi-point Forecasting
new_data <- data.frame(ad = c(11, 12, 13, 14, 15))
predict(model, new_data)
# [1] 23 25 27 29 31

# Confidence Interval
predict(model, data.frame(ad = 10), interval = "confidence")
#       fit    lwr    upr
# 1 21.000 20.751 21.249

(2) 予測区間

R
# Prediction Range (Includes uncertainty in individual predictions)
predict(model, data.frame(ad = 10), interval = "prediction")
#       fit    lwr    upr
# 1 21.000 20.064 21.936  <- wider than confidence


6. 残差の診断:plot.lm

(1) 4つの主要な診断チャート

R
par(mfrow = c(2, 2))
plot(model)
画像 意味 どうあるべきか
1. 残差と推定値 残差と推定値 ランダムに散らばっている(パターンなし)
2. QQプロット 残差の正規性 直線に近い点
3. スケール・位置 等分散性 水平線付近
4. 残差とレバレッジ レバレッジとその影響 ほとんどのデータ点は境界から遠く離れている

(2) 主要な診断

R
# Residual
residuals(model)

# Standardized Residuals
rstandard(model)

# Leverage Ratio
hatvalues(model)

# Cook's Distance (Impact Metrics)
cooks.distance(model)


7. 多重線形回帰

(1) 多重回帰

R
# Sales ~ Advertising expenses + Price + Season
df <- data.frame(
  sales = c(100, 120, 130, 110, 140, 150, 130, 160, 170, 180),
  ad = c(10, 12, 14, 11, 15, 16, 13, 17, 18, 19),
  price = c(50, 48, 45, 49, 44, 43, 47, 42, 41, 40),
  season = c("Spring", "Summer", "Autumn", "Winter", "Spring", "Summer", "Autumn", "Winter", "Spring", "Summer")
)

model <- lm(sales ~ ad + price + season, data = df)
summary(model)

(2) インタラクティブ項目

R
# Includes interaction terms (ad:price)
model <- lm(sales ~ ad * price, data = df)
# Equivalent to sales ~ ad + price + ad:price

(3) カテゴリ変数の自動エンコーディング

R character 変数を自動的に ダミー変数 に変換する:

R
# season is a character vector, R automatically creates:
# seasonSummer, seasonAutumn, seasonWinter (Spring as the Baseline)
💡 ヒントas.factor() 明示的な因子変換は、デフォルトの文字よりも安全です。



8. モデルの選択

(1) 調整済みR²

R
# The more variables you add, R-squared gets bigger (even if the variables are irrelevant)
# Adjusted R-squared corrects this bias
summary(model)$adj.r.squared

(2) AIC(情報量基準)

R
# AIC The smaller the model, the better
model1 <- lm(sales ~ ad, data = df)
model2 <- lm(sales ~ ad + price, data = df)
model3 <- lm(sales ~ ad + price + season, data = df)

AIC(model1, model2, model3)
#       df      AIC
# 1      3  85.32
# 2      4  78.45
# 3      6  72.18  ← Best

(3) 段階的な復帰

R
# Forward
step(lm(sales ~ 1, data = df),
     scope = list(lower = ~ 1, upper = ~ ad + price + season),
     direction = "forward")

# Back
step(model3, direction = "backward")

# Two-way
step(model1, scope = ~ ad + price + season, direction = "both")


9. 実践的な応用:包括的な売上予測モデル

以下は、このレッスンで取り上げた線形回帰の概念をすべて結びつけた完全なワークフローの例です。

▶ サンプル:統合型販売予測モデル

R
# ============================================
# Comprehensive Sales Forecasting Model
# Features: The Complete Linear Regression Process (Data Exploration -> Model -> Diagnosis -> Forecast)
# ============================================

library(ggplot2)
library(dplyr)
library(broom)

# 1. Prepare data
set.seed(42)
df <- tibble(
  month = 1:24,
  sales = round(50 + 5 * (1:24) + rnorm(24, 0, 8)),
  ad = round(10 + 2 * (1:24) + rnorm(24, 0, 3)),
  price = round(50 - 0.5 * (1:24) + rnorm(24, 0, 2)),
  season = rep(c("Spring", "Summer", "Autumn", "Winter"), 6),
  region = rep(c("Northern China", "East China", "South China", "Central China"), 6)
)

cat("=== Data Preview ===\n")
print(head(df, 3))

# 2. Data Exploration: Scatter Plot Matrix
cat("\n=== Correlation Analysis ===\n")
cor(df |> select(month, sales, ad, price))
cat("\n")

# 3. Simple Linear Regression
cat("=== Simple Regression: sales ~ ad ===\n")
model1 <- lm(sales ~ ad, data = df)
summary(model1)

# 4. Multiple Regression
cat("\n=== Multiple Regression: sales ~ ad + price + season ===\n")
model2 <- lm(sales ~ ad + price + season, data = df)
summary(model2)

# 5. Full Return
cat("\n=== Full Model: sales ~ ad + price + season + region ===\n")
model3 <- lm(sales ~ ad + price + season + region, data = df)
summary(model3)

# 6. Model Comparison
cat("\n=== Model Comparison ===\n")
cat("Model 1 (Advertisement Only): R-squared =", round(summary(model1)$r.squared, 3),
    "Adjusted R-squared =", round(summary(model1)$adj.r.squared, 3), "\n")
cat("Model 2 (+Price+Season): R-squared =", round(summary(model2)$r.squared, 3),
    "Adjusted R-squared =", round(summary(model2)$adj.r.squared, 3), "\n")
cat("Model 3 (+Region): R-squared =", round(summary(model3)$r.squared, 3),
    "Adjusted R-squared =", round(summary(model3)$adj.r.squared, 3), "\n")
cat("AIC:\n")
print(AIC(model1, model2, model3))

# 7. Model Diagnostics
cat("\n=== Model 3 Residual Diagnosis ===\n")
par(mfrow = c(2, 2))
plot(model3)
par(mfrow = c(1, 1))

# 8. Forecast
cat("\n=== Forecast for Next Month ===\n")
future <- data.frame(
  ad = 60,
  price = 38,
  season = "Autumn",
  region = "Northern China"
)
prediction <- predict(model3, future, interval = "confidence")
print(prediction)
cat("\nAnalysis: Sales Forecast for Next Month:", round(prediction[1, "fit"], 1), "10,000 yuan\n")
cat("95% Confidence Interval: [", round(prediction[1, "lwr"], 1), ", ",
    round(prediction[1, "upr"], 1), "]\n")

# 9. Residual Analysis
cat("\n=== Residual Analysis ===\n")
df <- df |>
  mutate(
    fitted = fitted(model3),
    residual = resid(model3),
    std_residual = rstandard(model3)
  )

cat("Maximum Positive Residual:", round(max(df$residual), 2),
    " (Sales were higher than expected)\n")
cat("Maximum Negative Residual:", round(min(df$residual), 2),
    " (Sales were lower than expected)\n")
cat("Standard Deviation of Residuals:", round(sd(df$residual), 2), "\n\n")

# 10. Coefficient Visualization
coef_df <- tidy(model3, conf.int = TRUE)
print(coef_df |> select(term, estimate, std.error, p.value, conf.low, conf.high))

# 11. Actual vs Fitting a Scatter Plot
ggplot(df, aes(x = fitted, y = sales)) +
  geom_point(size = 3, color = "blue") +
  geom_abline(slope = 1, intercept = 0, color = "red", linetype = "dashed") +
  labs(title = "Actual vs Fitting", x = "Fitted values", y = "Actual value") +
  theme_minimal()

# 12. Save Model
saveRDS(model3, "sales_model.rds")
cat("\n=== The model has been saved: sales_model.rds ===\n")
▶ 試してみよう

期待される出力(抜粋):

R
=== Full Model: sales ~ ad + price + season + region ===
Coefficients:
              Estimate Std. Error t value Pr(>|t|)    
(Intercept)    55.234      8.123   6.801 0.00001 ***
ad              4.876      0.234  20.838  < 2e-16 ***
price          -0.432      0.123  -3.512  0.00245 ** 
seasonSummer        5.234      1.876   2.789  0.01234 *  
seasonAutumn        2.123      1.876   1.132  0.27456    
seasonWinter       -3.456      1.876  -1.842  0.08345 .  
regionEast China      8.234      1.876   4.389  0.00045 ***
regionSouth China      3.456      1.876   1.842  0.08345 .  
regionCentral China      1.234      1.876   0.658  0.51894    
---
Signif. codes:  0 ‘*’ 0.001 ‘’ 0.01 ‘*’ 0.05 ‘.’ 0.1 ‘ ’ 1
Residual standard error: 4.234 on 15 degrees of freedom
Multiple R-squared:  0.9823,	Adjusted R-squared:  0.9734

=== Forecast for Next Month ===
       fit      lwr      upr
1 168.452 162.345 174.559

Analysis: Sales Forecast for Next Month: 168.5 10,000 yuan
95% Confidence Interval: [162.3, 174.6]

❓ よくある質問

Q 係数が有意でない場合はどうすればよいですか?
A 考えられる理由は4つあります:① 標本サイズが不十分である;② その変数が本質的に無関係である;③ 多重共線性(他の変数との相関)がある;④ 変数の変換が必要である。
Q 多重回帰分析において、変数はどのように選択すればよいですか?
A 3つの方法があります:① ビジネス上の理解(専門家の経験) ② ステップワイズ回帰 step() ③ 情報基準 AIC / BIC を用いて、最も単純なモデルを選択します。

📖 まとめ


📝 練習問題

  1. 基本演習:Rの組み込みデータセットmtcarsを使用してmpg ~ wt単純線形回帰を行い、summary()を用いてすべての出力を解釈し、wt = 3についてmpgを予測する。

  2. 基本的な問題:前の問題(par(mfrow = c(2, 2)); plot(model))のモデルについて、4つの診断プロットを描き、残差が正規分布に従い、等分散であるかどうかを確認しなさい。

  3. 基本的な問題:多重回帰モデル mpg ~ wt + cyl + hp を構築し、そのR²値と調整済みR²値を単純回帰のそれと比較してください。どちらが優れていますか?

  4. 応用演習:売上データ(売上対広告費+価格+季節)を100行分シミュレートします。以下の全プロセスを完了させてください:①探索 ②モデリング ③要約 ④診断 ⑤予測 ⑥可視化。モデルをRDSファイルとして保存してください。

  5. 課題問題mtcars を使用して、完全なモデル選択を行ってください: ① 4つのモデル(wtのみ / wt+cyl / wt+cyl+hp / wt+cyl+hp+disp)を実行する ② AICを用いて比較する ③ step()を使用して段階的回帰分析を行う ④ anova()を使用してネスト比較を行う ⑤ 最適なモデルを選択し、予測を行う。プロセスを記録するためにスクリーンショットを撮影すること。

Web-Tutorial.com

Web-Tutorial 技術チーム

複数の開発者によって共同維持されているプログラミングチュートリアルプラットフォーム。各チュートリアルは専門分野の開発者が執筆・レビューしています。正確で信頼性の高いコンテンツを目指しています — 問題を見つけた場合はお知らせください。

100%