# 1. 載入套件
library(readxl)
## Warning: package 'readxl' was built under R version 4.5.2
library(dplyr)
## Warning: package 'dplyr' was built under R version 4.5.2
##
## Attaching package: 'dplyr'
## The following objects are masked from 'package:stats':
##
## filter, lag
## The following objects are masked from 'package:base':
##
## intersect, setdiff, setequal, union
library(tidyr)
## Warning: package 'tidyr' was built under R version 4.5.2
library(ggplot2)
## Warning: package 'ggplot2' was built under R version 4.5.2
library(sandwich)
# 2. 讀取 Excel
raw <- read_excel(
"~/Desktop/wh/Asean1029.xlsx",
.name_repair = "unique"
)
## New names:
## • `Trade China GDP ratio old` -> `Trade China GDP ratio old...13`
## • `Trade China GDP ratio old` -> `Trade China GDP ratio old...14`
# 3. 清除欄位名稱前後空格
names(raw) <- trimws(names(raw))
# 4. 整理變數
d <- raw %>%
transmute(
Country = as.character(Country),
Year = as.integer(Year),
UNGA = as.numeric(`UNGA Position Index`),
ISEAS = as.numeric(`ISEAS Elite preference`),
Democracy = as.numeric(`Democracy EIU`),
SCS = as.numeric(SCS),
Post2022 = as.integer(Year >= 2022),
PolStab = as.numeric(`Political Stability`),
FSI = as.numeric(`FSI (100 - raw FSI)`),
USAlly = as.numeric(
`US Formal Defense Ally (1/0)`
),
TradeChina = as.numeric(raw[[14]])
)
# 5. 建立 UNGA 回歸資料
unga_data <- d %>%
drop_na(
Country, UNGA, Democracy, SCS,
Post2022, TradeChina, USAlly,
PolStab, FSI
)
# 6. 建立 ISEAS 回歸資料
iseas_data <- d %>%
drop_na(
Country, ISEAS, Democracy, SCS,
Post2022, TradeChina, USAlly,
PolStab, FSI
)
library(readxl)
library(dplyr)
library(tidyr)
# 1. 讀取 Excel
raw <- read_excel(
"~/Desktop/wh/Asean1029.xlsx",
.name_repair = "unique"
)
## New names:
## • `Trade China GDP ratio old` -> `Trade China GDP ratio old...13`
## • `Trade China GDP ratio old` -> `Trade China GDP ratio old...14`
# 2. 清除欄位名稱前後空格
names(raw) <- trimws(names(raw))
# 3. 整理研究變數
d <- raw %>%
transmute(
Country = as.character(Country),
Year = as.integer(Year),
# 依變數
UNGA = as.numeric(`UNGA Position Index`),
ISEAS = as.numeric(`ISEAS Elite preference`),
# 核心自變數
Democracy = as.numeric(`Democracy EIU`),
SCS = as.numeric(SCS),
Post2022 = as.integer(Year >= 2022),
# 控制變數
TradeChina = as.numeric(raw[[14]]),
USAlly = as.numeric(`US Formal Defense Ally (1/0)`),
PolStab = as.numeric(`Political Stability`),
FSI = as.numeric(`FSI (100 - raw FSI)`)
)
# 4. 確認資料
head(d)
## # A tibble: 6 × 11
## Country Year UNGA ISEAS Democracy SCS Post2022 TradeChina USAlly PolStab
## <chr> <int> <dbl> <dbl> <dbl> <dbl> <int> <dbl> <dbl> <dbl>
## 1 Cambodia 2010 1.01 NA 4.87 0 0 0.0906 0 58.3
## 2 Cambodia 2011 1.11 NA 4.87 0 0 0.118 0 59.4
## 3 Cambodia 2012 0.844 NA 4.96 0 0 0.135 0 58.6
## 4 Cambodia 2013 1.09 NA 4.6 0 0 0.165 0 58.6
## 5 Cambodia 2014 0.949 NA 4.78 0 0 0.334 0 60.2
## 6 Cambodia 2015 1.50 NA 4.27 0 0 0.346 0 62.1
## # ℹ 1 more variable: FSI <dbl>
names(d)
## [1] "Country" "Year" "UNGA" "ISEAS" "Democracy"
## [6] "SCS" "Post2022" "TradeChina" "USAlly" "PolStab"
## [11] "FSI"
nrow(d)
## [1] 128
# =====================================
# Step 2: Check Available Observations
# =====================================
# 1. UNGA:完整模型可用資料
unga_data <- d %>%
drop_na(
Country, UNGA, Democracy, SCS, Post2022,
TradeChina, USAlly, PolStab, FSI
)
# 2. ISEAS:完整模型可用資料
iseas_data <- d %>%
drop_na(
Country, ISEAS, Democracy, SCS, Post2022,
TradeChina, USAlly, PolStab, FSI
)
# 3. 檢查樣本數與年份
data.frame(
Model = c("UNGA", "ISEAS"),
N = c(nrow(unga_data), nrow(iseas_data)),
StartYear = c(
min(unga_data$Year),
min(iseas_data$Year)
),
EndYear = c(
max(unga_data$Year),
max(iseas_data$Year)
),
Countries = c(
n_distinct(unga_data$Country),
n_distinct(iseas_data$Country)
)
)
## Model N StartYear EndYear Countries
## 1 UNGA 120 2010 2024 8
## 2 ISEAS 48 2019 2024 8
# =====================================
# Step 3: OLS Regression Models
# =====================================
# UNGA Position Index
# M1:核心自變數
m1 <- lm(
UNGA ~ Democracy + SCS + Post2022,
data = unga_data
)
# M2:加入主要控制變數
m2 <- lm(
UNGA ~ Democracy + SCS + Post2022 +
TradeChina + USAlly,
data = unga_data
)
# M3:完整模型
m3 <- lm(
UNGA ~ Democracy + SCS + Post2022 +
TradeChina + USAlly + PolStab + FSI,
data = unga_data
)
# ISEAS Elite Preference
# M4:核心自變數
m4 <- lm(
ISEAS ~ Democracy + SCS + Post2022,
data = iseas_data
)
# M5:加入主要控制變數
m5 <- lm(
ISEAS ~ Democracy + SCS + Post2022 +
TradeChina + USAlly,
data = iseas_data
)
# M6:完整模型
m6 <- lm(
ISEAS ~ Democracy + SCS + Post2022 +
TradeChina + USAlly + PolStab + FSI,
data = iseas_data
)
# 查看六組模型結果
summary(m1)
##
## Call:
## lm(formula = UNGA ~ Democracy + SCS + Post2022, data = unga_data)
##
## Residuals:
## Min 1Q Median 3Q Max
## -0.38597 -0.12766 -0.00277 0.10456 0.50185
##
## Coefficients:
## Estimate Std. Error t value Pr(>|t|)
## (Intercept) 1.39894 0.05595 25.005 < 2e-16 ***
## Democracy -0.05487 0.01020 -5.380 3.92e-07 ***
## SCS 0.02458 0.03748 0.656 0.513
## Post2022 -0.40730 0.04488 -9.076 3.47e-15 ***
## ---
## Signif. codes: 0 '***' 0.001 '**' 0.01 '*' 0.05 '.' 0.1 ' ' 1
##
## Residual standard error: 0.1966 on 116 degrees of freedom
## Multiple R-squared: 0.4862, Adjusted R-squared: 0.4729
## F-statistic: 36.59 on 3 and 116 DF, p-value: < 2.2e-16
summary(m2)
##
## Call:
## lm(formula = UNGA ~ Democracy + SCS + Post2022 + TradeChina +
## USAlly, data = unga_data)
##
## Residuals:
## Min 1Q Median 3Q Max
## -0.42404 -0.11632 -0.01333 0.14055 0.42105
##
## Coefficients:
## Estimate Std. Error t value Pr(>|t|)
## (Intercept) 1.39640 0.07481 18.665 < 2e-16 ***
## Democracy -0.04213 0.01076 -3.917 0.000153 ***
## SCS 0.04357 0.03544 1.230 0.221409
## Post2022 -0.39777 0.04363 -9.117 3.15e-15 ***
## TradeChina -0.12057 0.17509 -0.689 0.492462
## USAlly -0.19015 0.04384 -4.338 3.12e-05 ***
## ---
## Signif. codes: 0 '***' 0.001 '**' 0.01 '*' 0.05 '.' 0.1 ' ' 1
##
## Residual standard error: 0.1834 on 114 degrees of freedom
## Multiple R-squared: 0.5606, Adjusted R-squared: 0.5413
## F-statistic: 29.09 on 5 and 114 DF, p-value: < 2.2e-16
summary(m3)
##
## Call:
## lm(formula = UNGA ~ Democracy + SCS + Post2022 + TradeChina +
## USAlly + PolStab + FSI, data = unga_data)
##
## Residuals:
## Min 1Q Median 3Q Max
## -0.39378 -0.10970 -0.00452 0.12027 0.43113
##
## Coefficients:
## Estimate Std. Error t value Pr(>|t|)
## (Intercept) 1.540379 0.236814 6.505 2.26e-09 ***
## Democracy -0.024204 0.015667 -1.545 0.125
## SCS 0.024443 0.034543 0.708 0.481
## Post2022 -0.384650 0.042393 -9.073 4.53e-15 ***
## TradeChina 0.175948 0.191510 0.919 0.360
## USAlly -0.274630 0.058201 -4.719 6.91e-06 ***
## PolStab -0.003023 0.003644 -0.829 0.409
## FSI -0.002608 0.002399 -1.087 0.279
## ---
## Signif. codes: 0 '***' 0.001 '**' 0.01 '*' 0.05 '.' 0.1 ' ' 1
##
## Residual standard error: 0.1764 on 112 degrees of freedom
## Multiple R-squared: 0.6009, Adjusted R-squared: 0.576
## F-statistic: 24.09 on 7 and 112 DF, p-value: < 2.2e-16
summary(m4)
##
## Call:
## lm(formula = ISEAS ~ Democracy + SCS + Post2022, data = iseas_data)
##
## Residuals:
## Min 1Q Median 3Q Max
## -33.389 -15.838 -0.067 11.716 34.599
##
## Coefficients:
## Estimate Std. Error t value Pr(>|t|)
## (Intercept) 56.019 7.954 7.043 9.89e-09 ***
## Democracy -5.589 1.391 -4.018 0.000226 ***
## SCS 23.554 5.699 4.133 0.000158 ***
## Post2022 -6.570 5.417 -1.213 0.231633
## ---
## Signif. codes: 0 '***' 0.001 '**' 0.01 '*' 0.05 '.' 0.1 ' ' 1
##
## Residual standard error: 18.76 on 44 degrees of freedom
## Multiple R-squared: 0.4002, Adjusted R-squared: 0.3593
## F-statistic: 9.785 on 3 and 44 DF, p-value: 4.594e-05
summary(m5)
##
## Call:
## lm(formula = ISEAS ~ Democracy + SCS + Post2022 + TradeChina +
## USAlly, data = iseas_data)
##
## Residuals:
## Min 1Q Median 3Q Max
## -28.508 -13.370 -0.626 12.638 41.630
##
## Coefficients:
## Estimate Std. Error t value Pr(>|t|)
## (Intercept) 76.329 14.822 5.150 6.54e-06 ***
## Democracy -7.950 1.823 -4.361 8.22e-05 ***
## SCS 25.063 5.773 4.341 8.75e-05 ***
## Post2022 -5.288 5.366 -0.985 0.330
## TradeChina -45.105 30.771 -1.466 0.150
## USAlly 5.802 7.113 0.816 0.419
## ---
## Signif. codes: 0 '***' 0.001 '**' 0.01 '*' 0.05 '.' 0.1 ' ' 1
##
## Residual standard error: 18.34 on 42 degrees of freedom
## Multiple R-squared: 0.453, Adjusted R-squared: 0.3879
## F-statistic: 6.958 on 5 and 42 DF, p-value: 8.196e-05
summary(m6)
##
## Call:
## lm(formula = ISEAS ~ Democracy + SCS + Post2022 + TradeChina +
## USAlly + PolStab + FSI, data = iseas_data)
##
## Residuals:
## Min 1Q Median 3Q Max
## -27.905 -12.645 -3.152 8.675 34.670
##
## Coefficients:
## Estimate Std. Error t value Pr(>|t|)
## (Intercept) 86.8143 37.4752 2.317 0.025732 *
## Democracy -10.4312 2.8067 -3.716 0.000618 ***
## SCS 26.5384 5.8962 4.501 5.72e-05 ***
## Post2022 -5.8967 5.3668 -1.099 0.278458
## TradeChina -60.6256 32.4169 -1.870 0.068789 .
## USAlly 10.9506 8.4203 1.301 0.200872
## PolStab -0.1522 0.5620 -0.271 0.787881
## FSI 0.4040 0.3887 1.039 0.304945
## ---
## Signif. codes: 0 '***' 0.001 '**' 0.01 '*' 0.05 '.' 0.1 ' ' 1
##
## Residual standard error: 18.29 on 40 degrees of freedom
## Multiple R-squared: 0.482, Adjusted R-squared: 0.3914
## F-statistic: 5.318 on 7 and 40 DF, p-value: 0.0002351
# =====================================
# Step 4-1: Define get_coef Function
# =====================================
library(broom)
library(lmtest)
## Loading required package: zoo
## Warning: package 'zoo' was built under R version 4.5.2
##
## Attaching package: 'zoo'
## The following objects are masked from 'package:base':
##
## as.Date, as.Date.numeric
library(sandwich)
library(dplyr)
get_coef <- function(model, data, label) {
# 計算國家叢集標準誤
V <- sandwich::vcovCL(
model,
cluster = data$Country,
type = "HC1"
)
# 提取迴歸係數及標準誤
result <- broom::tidy(
lmtest::coeftest(model, vcov. = V)
)
# 國家數量
G <- dplyr::n_distinct(data$Country)
# 95% 信賴區間
critical <- qt(0.975, df = G - 1)
result %>%
dplyr::mutate(
conf.low = estimate - critical * std.error,
conf.high = estimate + critical * std.error,
Model = label
)
}
# =====================================
# Step 4-2: Prepare Coefficient Data
# =====================================
coef_data <- dplyr::bind_rows(
get_coef(m3, unga_data, "UNGA Position Index"),
get_coef(m6, iseas_data, "ISEAS Elite Preference")
) %>%
dplyr::filter(term != "(Intercept)") %>%
dplyr::mutate(
Variable = dplyr::recode(
term,
"Democracy" = "Democracy",
"SCS" = "SCS Claimant",
"Post2022" = "Post-2022",
"TradeChina" = "Trade with China",
"USAlly" = "U.S. Defense Ally",
"PolStab" = "Political Stability",
"FSI" = "State Capacity"
),
Variable = factor(
Variable,
levels = rev(c(
"Democracy",
"SCS Claimant",
"Post-2022",
"Trade with China",
"U.S. Defense Ally",
"Political Stability",
"State Capacity"
))
)
)
# 確認整理成功
print(coef_data)
## # A tibble: 14 × 9
## term estimate std.error statistic p.value conf.low conf.high Model Variable
## <chr> <dbl> <dbl> <dbl> <dbl> <dbl> <dbl> <chr> <fct>
## 1 Demo… -2.42e-2 0.0111 -2.18 3.13e- 2 -5.05e-2 0.00205 UNGA… Democra…
## 2 SCS 2.44e-2 0.0249 0.983 3.28e- 1 -3.44e-2 0.0833 UNGA… SCS Cla…
## 3 Post… -3.85e-1 0.0433 -8.88 1.24e-14 -4.87e-1 -0.282 UNGA… Post-20…
## 4 Trad… 1.76e-1 0.137 1.28 2.02e- 1 -1.48e-1 0.500 UNGA… Trade w…
## 5 USAl… -2.75e-1 0.0755 -3.64 4.18e- 4 -4.53e-1 -0.0961 UNGA… U.S. De…
## 6 PolS… -3.02e-3 0.00461 -0.655 5.14e- 1 -1.39e-2 0.00788 UNGA… Politic…
## 7 FSI -2.61e-3 0.00292 -0.894 3.73e- 1 -9.50e-3 0.00429 UNGA… State C…
## 8 Demo… -1.04e+1 3.11 -3.36 1.74e- 3 -1.78e+1 -3.08 ISEA… Democra…
## 9 SCS 2.65e+1 7.74 3.43 1.42e- 3 8.24e+0 44.8 ISEA… SCS Cla…
## 10 Post… -5.90e+0 4.95 -1.19 2.41e- 1 -1.76e+1 5.81 ISEA… Post-20…
## 11 Trad… -6.06e+1 37.6 -1.61 1.14e- 1 -1.49e+2 28.2 ISEA… Trade w…
## 12 USAl… 1.10e+1 11.2 0.982 3.32e- 1 -1.54e+1 37.3 ISEA… U.S. De…
## 13 PolS… -1.52e-1 0.453 -0.336 7.39e- 1 -1.22e+0 0.919 ISEA… Politic…
## 14 FSI 4.04e-1 0.383 1.05 2.98e- 1 -5.02e-1 1.31 ISEA… State C…
# =====================================
# Step 5: Grayscale Coefficient Plot
# =====================================
library(ggplot2)
p_coef <- ggplot(
coef_data,
aes(x = estimate, y = Variable)
) +
# 係數為零的參考線
geom_vline(
xintercept = 0,
linetype = "dashed",
color = "gray65",
linewidth = 0.6
) +
# 95% 信賴區間
geom_errorbar(
aes(xmin = conf.low, xmax = conf.high),
orientation = "y",
width = 0.15,
linewidth = 0.8,
color = "gray35"
) +
# 迴歸係數
geom_point(
size = 3.2,
shape = 21,
fill = "black",
color = "white",
stroke = 0.5
) +
# 分成 UNGA 和 ISEAS 兩個面板
facet_wrap(
~ Model,
scales = "free_x",
nrow = 1
) +
labs(
title = "Determinants of ASEAN Strategic Positioning",
subtitle = "OLS Coefficients with 95% Confidence Intervals",
x = "Coefficient Estimate",
y = NULL,
caption = "Country-clustered standard errors (8 countries)."
) +
theme_classic(base_size = 14) +
theme(
plot.title = element_text(
face = "bold",
size = 18
),
plot.subtitle = element_text(
color = "gray40",
size = 12
),
strip.text = element_text(
face = "bold",
size = 12
),
strip.background = element_rect(
fill = "gray92",
color = NA
),
panel.spacing = grid::unit(1.5, "lines"),
axis.text.y = element_text(
size = 11,
color = "gray20"
),
plot.caption = element_text(
size = 9,
color = "gray45"
),
plot.margin = margin(18, 20, 15, 15)
)
# 顯示圖片
print(p_coef)

# =====================================
# Step 7: Interaction Regression Models
# =====================================
# M7:UNGA × Democracy × Post2022
m7 <- lm(
UNGA ~ Democracy * Post2022 +
SCS + TradeChina + USAlly +
PolStab + FSI,
data = unga_data
)
# M8:UNGA × Democracy × SCS
m8 <- lm(
UNGA ~ Democracy * SCS +
Post2022 + TradeChina + USAlly +
PolStab + FSI,
data = unga_data
)
# M9:ISEAS × Democracy × Post2022
m9 <- lm(
ISEAS ~ Democracy * Post2022 +
SCS + TradeChina + USAlly +
PolStab + FSI,
data = iseas_data
)
# M10:ISEAS × Democracy × SCS
m10 <- lm(
ISEAS ~ Democracy * SCS +
Post2022 + TradeChina + USAlly +
PolStab + FSI,
data = iseas_data
)
# 查看四組迴歸結果
summary(m7)
##
## Call:
## lm(formula = UNGA ~ Democracy * Post2022 + SCS + TradeChina +
## USAlly + PolStab + FSI, data = unga_data)
##
## Residuals:
## Min 1Q Median 3Q Max
## -0.39476 -0.10521 -0.00414 0.13043 0.41947
##
## Coefficients:
## Estimate Std. Error t value Pr(>|t|)
## (Intercept) 1.571794 0.236552 6.645 1.18e-09 ***
## Democracy -0.030403 0.016144 -1.883 0.0623 .
## Post2022 -0.545334 0.116978 -4.662 8.78e-06 ***
## SCS 0.022047 0.034402 0.641 0.5229
## TradeChina 0.246229 0.196405 1.254 0.2126
## USAlly -0.274202 0.057901 -4.736 6.49e-06 ***
## PolStab -0.003155 0.003626 -0.870 0.3862
## FSI -0.002736 0.002388 -1.146 0.2543
## Democracy:Post2022 0.030942 0.021011 1.473 0.1437
## ---
## Signif. codes: 0 '***' 0.001 '**' 0.01 '*' 0.05 '.' 0.1 ' ' 1
##
## Residual standard error: 0.1754 on 111 degrees of freedom
## Multiple R-squared: 0.6086, Adjusted R-squared: 0.5804
## F-statistic: 21.57 on 8 and 111 DF, p-value: < 2.2e-16
summary(m8)
##
## Call:
## lm(formula = UNGA ~ Democracy * SCS + Post2022 + TradeChina +
## USAlly + PolStab + FSI, data = unga_data)
##
## Residuals:
## Min 1Q Median 3Q Max
## -0.39932 -0.11749 -0.00476 0.12367 0.43175
##
## Coefficients:
## Estimate Std. Error t value Pr(>|t|)
## (Intercept) 1.470545 0.315464 4.662 8.79e-06 ***
## Democracy -0.018435 0.023254 -0.793 0.430
## SCS 0.069444 0.138036 0.503 0.616
## Post2022 -0.381647 0.043485 -8.776 2.31e-14 ***
## TradeChina 0.170956 0.192843 0.887 0.377
## USAlly -0.265885 0.063941 -4.158 6.34e-05 ***
## PolStab -0.002086 0.004595 -0.454 0.651
## FSI -0.003267 0.003103 -1.053 0.295
## Democracy:SCS -0.008564 0.025427 -0.337 0.737
## ---
## Signif. codes: 0 '***' 0.001 '**' 0.01 '*' 0.05 '.' 0.1 ' ' 1
##
## Residual standard error: 0.1771 on 111 degrees of freedom
## Multiple R-squared: 0.6013, Adjusted R-squared: 0.5726
## F-statistic: 20.93 on 8 and 111 DF, p-value: < 2.2e-16
summary(m9)
##
## Call:
## lm(formula = ISEAS ~ Democracy * Post2022 + SCS + TradeChina +
## USAlly + PolStab + FSI, data = iseas_data)
##
## Residuals:
## Min 1Q Median 3Q Max
## -29.105 -13.755 -1.354 9.885 35.675
##
## Coefficients:
## Estimate Std. Error t value Pr(>|t|)
## (Intercept) 90.2152 38.0385 2.372 0.022739 *
## Democracy -11.2813 3.0797 -3.663 0.000739 ***
## Post2022 -15.5550 14.9408 -1.041 0.304237
## SCS 26.4649 5.9358 4.458 6.8e-05 ***
## TradeChina -56.9523 33.0567 -1.723 0.092834 .
## USAlly 11.1410 8.4799 1.314 0.196586
## PolStab -0.1475 0.5657 -0.261 0.795634
## FSI 0.3965 0.3914 1.013 0.317379
## Democracy:Post2022 1.8875 2.7223 0.693 0.492202
## ---
## Signif. codes: 0 '***' 0.001 '**' 0.01 '*' 0.05 '.' 0.1 ' ' 1
##
## Residual standard error: 18.41 on 39 degrees of freedom
## Multiple R-squared: 0.4883, Adjusted R-squared: 0.3834
## F-statistic: 4.653 on 8 and 39 DF, p-value: 0.0004757
summary(m10)
##
## Call:
## lm(formula = ISEAS ~ Democracy * SCS + Post2022 + TradeChina +
## USAlly + PolStab + FSI, data = iseas_data)
##
## Residuals:
## Min 1Q Median 3Q Max
## -31.125 -12.476 -1.477 10.960 35.417
##
## Coefficients:
## Estimate Std. Error t value Pr(>|t|)
## (Intercept) 205.855 91.092 2.260 0.0295 *
## Democracy -20.873 7.809 -2.673 0.0109 *
## SCS -30.835 40.539 -0.761 0.4515
## Post2022 -6.974 5.351 -1.303 0.2001
## TradeChina -57.567 32.073 -1.795 0.0804 .
## USAlly 10.567 8.317 1.271 0.2114
## PolStab -1.906 1.346 -1.416 0.1647
## FSI 1.746 1.014 1.722 0.0930 .
## Democracy:SCS 10.686 7.472 1.430 0.1607
## ---
## Signif. codes: 0 '***' 0.001 '**' 0.01 '*' 0.05 '.' 0.1 ' ' 1
##
## Residual standard error: 18.05 on 39 degrees of freedom
## Multiple R-squared: 0.5078, Adjusted R-squared: 0.4069
## F-statistic: 5.03 on 8 and 39 DF, p-value: 0.0002478
# =====================================
# Interaction Prediction Data
# =====================================
library(dplyr)
library(sandwich)
make_prediction <- function(model, data, groupvar) {
# 建立民主指數範圍
pred <- expand.grid(
Democracy = seq(
min(data$Democracy, na.rm = TRUE),
max(data$Democracy, na.rm = TRUE),
length.out = 100
),
Group = c(0, 1)
)
# 其他變數固定在樣本平均值
pred$Post2022 <- mean(data$Post2022, na.rm = TRUE)
pred$SCS <- mean(data$SCS, na.rm = TRUE)
pred$TradeChina <- mean(data$TradeChina, na.rm = TRUE)
pred$USAlly <- mean(data$USAlly, na.rm = TRUE)
pred$PolStab <- mean(data$PolStab, na.rm = TRUE)
pred$FSI <- mean(data$FSI, na.rm = TRUE)
# 設定比較組別
pred[[groupvar]] <- pred$Group
# 國家叢集共變異數矩陣
V <- sandwich::vcovCL(
model,
cluster = data$Country,
type = "HC1"
)
# 計算預測值與標準誤
X <- model.matrix(
delete.response(terms(model)),
data = pred
)
pred$fit <- as.vector(X %*% coef(model))
pred$se <- sqrt(
pmax(0, rowSums((X %*% V) * X))
)
# 95% 信賴區間
G <- dplyr::n_distinct(data$Country)
critical <- qt(0.975, df = G - 1)
pred$lower <- pred$fit - critical * pred$se
pred$upper <- pred$fit + critical * pred$se
# 組別名稱
if (groupvar == "Post2022") {
pred$Category <- factor(
pred$Group,
levels = c(0, 1),
labels = c("Pre-2022", "Post-2022")
)
} else {
pred$Category <- factor(
pred$Group,
levels = c(0, 1),
labels = c("Non-Claimant", "SCS Claimant")
)
}
return(pred)
}
# =====================================
# 建立四組預測資料
# =====================================
pred1 <- make_prediction(m7, unga_data, "Post2022")
pred2 <- make_prediction(m8, unga_data, "SCS")
pred3 <- make_prediction(m9, iseas_data, "Post2022")
pred4 <- make_prediction(m10, iseas_data, "SCS")
# 確認成功
names(pred1)
## [1] "Democracy" "Group" "Post2022" "SCS" "TradeChina"
## [6] "USAlly" "PolStab" "FSI" "fit" "se"
## [11] "lower" "upper" "Category"
head(pred1)
## Democracy Group Post2022 SCS TradeChina USAlly PolStab FSI fit
## 1 1.710000 0 0 0.375 0.2009302 0.25 63.11227 30.2703 1.227073
## 2 1.766465 0 0 0.375 0.2009302 0.25 63.11227 30.2703 1.225356
## 3 1.822929 0 0 0.375 0.2009302 0.25 63.11227 30.2703 1.223640
## 4 1.879394 0 0 0.375 0.2009302 0.25 63.11227 30.2703 1.221923
## 5 1.935859 0 0 0.375 0.2009302 0.25 63.11227 30.2703 1.220206
## 6 1.992323 0 0 0.375 0.2009302 0.25 63.11227 30.2703 1.218490
## se lower upper Category
## 1 0.05025476 1.108239 1.345907 Pre-2022
## 2 0.04940771 1.108526 1.342187 Pre-2022
## 3 0.04856194 1.108809 1.338471 Pre-2022
## 4 0.04771751 1.109089 1.334757 Pre-2022
## 5 0.04687450 1.109366 1.331047 Pre-2022
## 6 0.04603298 1.109639 1.327340 Pre-2022
# =====================================
# Grayscale Interaction Plots
# =====================================
library(ggplot2)
library(dplyr)
# 1. 灰階繪圖函數
plot_interaction <- function(pred, title, subtitle, ylabel) {
# 自動統一信賴區間欄位
if (all(c("conf.low", "conf.high") %in% names(pred))) {
pred$lower <- pred$conf.low
pred$upper <- pred$conf.high
} else if (all(c("low", "high") %in% names(pred))) {
pred$lower <- pred$low
pred$upper <- pred$high
}
# 自動建立組別標籤
if (!"Category" %in% names(pred)) {
if ("Period" %in% names(pred)) {
pred$Category <- pred$Period
} else if ("SCS_Group" %in% names(pred)) {
pred$Category <- pred$SCS_Group
} else if ("Post2022" %in% names(pred) &&
length(unique(pred$Post2022)) == 2) {
pred$Category <- ifelse(
pred$Post2022 == 1, "Post-2022", "Pre-2022"
)
} else if ("SCS" %in% names(pred) &&
length(unique(pred$SCS)) == 2) {
pred$Category <- ifelse(
pred$SCS == 1, "SCS Claimant", "Non-Claimant"
)
}
}
# 確認必要欄位存在
required <- c(
"Democracy", "fit", "lower", "upper", "Category"
)
missing <- setdiff(required, names(pred))
if (length(missing) > 0) {
stop(
"Missing columns: ",
paste(missing, collapse = ", ")
)
}
pred$Category <- factor(pred$Category)
groups <- levels(pred$Category)
# 繪圖
ggplot(
pred,
aes(x = Democracy, y = fit, group = Category)
) +
geom_ribbon(
aes(
ymin = lower,
ymax = upper,
fill = Category
),
alpha = 0.22,
colour = NA
) +
geom_line(
aes(
linetype = Category,
colour = Category
),
linewidth = 1.2
) +
scale_colour_manual(
values = setNames(
c("#666666", "#111111"),
groups
)
) +
scale_fill_manual(
values = setNames(
c("#BBBBBB", "#777777"),
groups
)
) +
scale_linetype_manual(
values = setNames(
c("dashed", "solid"),
groups
)
) +
labs(
title = title,
subtitle = subtitle,
x = "Democracy Index (EIU)",
y = ylabel,
colour = NULL,
fill = NULL,
linetype = NULL,
caption = "OLS predictions with 95% confidence intervals."
) +
theme_classic(base_size = 14) +
theme(
plot.title = element_text(
face = "bold",
size = 19
),
plot.subtitle = element_text(
colour = "gray40",
size = 12
),
axis.title = element_text(
face = "bold",
size = 13
),
axis.text = element_text(
colour = "gray30",
size = 11
),
legend.position = "bottom",
legend.text = element_text(size = 12),
legend.key.width = grid::unit(2.5, "cm"),
plot.caption = element_text(
colour = "gray50",
size = 9
)
) +
guides(
fill = "none",
linetype = "none"
)
}
# =====================================
# 2. 建立四張圖
# =====================================
p1 <- plot_interaction(
pred1,
"Democracy × Post-2022",
"Changes in Diplomatic Positioning",
"Predicted UNGA Position Index"
)
p2 <- plot_interaction(
pred2,
"Democracy × SCS Claimant",
"Differences by South China Sea Exposure",
"Predicted UNGA Position Index"
)
p3 <- plot_interaction(
pred3,
"Democracy × Post-2022",
"Changes in Elite Strategic Preferences",
"Predicted Elite Preference Distance"
)
p4 <- plot_interaction(
pred4,
"Democracy × SCS Claimant",
"Differences by South China Sea Exposure",
"Predicted Elite Preference Distance"
)
# =====================================
# 3. 顯示圖片
# =====================================
print(p1)

print(p2)

print(p3)

print(p4)

# =====================================
# 4. 儲存圖片
# =====================================
plots <- list(
Interaction_UNGA_Post2022 = p1,
Interaction_UNGA_SCS = p2,
Interaction_ISEAS_Post2022 = p3,
Interaction_ISEAS_SCS = p4
)
for (name in names(plots)) {
ggsave(
filename = file.path(
path.expand("~/Desktop/wh"),
paste0(name, ".png")
),
plot = plots[[name]],
width = 9,
height = 6,
dpi = 300,
bg = "white"
)
}
# =====================================
# Step 13: Robustness Check
# OLS vs Country Fixed Effects
# =====================================
library(dplyr)
library(fixest)
## Warning: package 'fixest' was built under R version 4.5.2
library(modelsummary)
## Warning: package 'modelsummary' was built under R version 4.5.2
# UNGA:Country Fixed Effects
fe_unga <- feols(
UNGA ~ Democracy + Post2022 +
TradeChina + PolStab + FSI | Country,
data = unga_data,
vcov = ~ Country
)
# ISEAS:Country Fixed Effects
fe_iseas <- feols(
ISEAS ~ Democracy + Post2022 +
TradeChina + PolStab + FSI | Country,
data = iseas_data,
vcov = ~ Country
)
# 比較 OLS 與 FE
robust_models <- list(
"UNGA OLS" = m3,
"UNGA Country FE" = fe_unga,
"ISEAS OLS" = m6,
"ISEAS Country FE" = fe_iseas
)
# 顯示迴歸表
modelsummary(
robust_models,
vcov = list(
sandwich::vcovCL(m3, cluster = unga_data$Country),
~ Country,
sandwich::vcovCL(m6, cluster = iseas_data$Country),
~ Country
),
coef_omit = "Intercept|SCS|USAlly",
statistic = "({std.error})",
stars = TRUE,
output = "gt"
)
| |
UNGA OLS |
UNGA Country FE |
ISEAS OLS |
ISEAS Country FE |
| Democracy |
-0.024* |
-0.022 |
-10.431** |
-9.874 |
|
(0.011) |
(0.035) |
(3.108) |
(19.348) |
| Post2022 |
-0.385*** |
-0.520*** |
-5.897 |
-9.958 |
|
(0.043) |
(0.064) |
(4.951) |
(8.529) |
| TradeChina |
0.176 |
0.355 |
-60.626 |
3.250 |
|
(0.137) |
(0.263) |
(37.558) |
(56.105) |
| PolStab |
-0.003 |
0.013* |
-0.152 |
-0.067 |
|
(0.005) |
(0.005) |
(0.453) |
(1.708) |
| FSI |
-0.003 |
0.005 |
0.404 |
1.043 |
|
(0.003) |
(0.005) |
(0.383) |
(2.369) |
| Num.Obs. |
120 |
120 |
48 |
48 |
| R2 |
0.601 |
0.678 |
0.482 |
0.613 |
| R2 Adj. |
0.576 |
0.642 |
0.391 |
0.480 |
| R2 Within |
|
0.559 |
|
0.076 |
| R2 Within Adj. |
|
0.538 |
|
-0.056 |
| AIC |
-66.2 |
-83.9 |
424.5 |
418.5 |
| BIC |
-41.1 |
-47.7 |
441.3 |
442.8 |
| Log.Lik. |
42.096 |
|
-203.232 |
|
| RMSE |
0.17 |
0.15 |
16.69 |
14.44 |
| Std.Errors |
Custom |
by: Country |
Custom |
by: Country |
| FE: Country |
|
X |
|
X |
| + p < 0.1, * p < 0.05, ** p < 0.01, *** p < 0.001 |
# =====================================
# Step 14: Robustness Coefficient Plot
# =====================================
library(ggplot2)
library(dplyr)
library(broom)
library(sandwich)
# 提取係數
get_robust_coef <- function(model, model_name, V = NULL) {
if (inherits(model, "fixest")) {
ct <- summary(model)$coeftable
result <- data.frame(
term = rownames(ct),
estimate = ct[, 1],
std.error = ct[, 2]
)
} else {
ct <- lmtest::coeftest(model, vcov. = V)
result <- broom::tidy(ct)
}
result %>%
mutate(
conf.low = estimate - qt(0.975, 7) * std.error,
conf.high = estimate + qt(0.975, 7) * std.error,
Model = model_name
)
}
robust_data <- bind_rows(
get_robust_coef(
m3, "UNGA OLS",
sandwich::vcovCL(m3, cluster = unga_data$Country)
),
get_robust_coef(fe_unga, "UNGA Country FE"),
get_robust_coef(
m6, "ISEAS OLS",
sandwich::vcovCL(m6, cluster = iseas_data$Country)
),
get_robust_coef(fe_iseas, "ISEAS Country FE")
) %>%
filter(term %in% c(
"Democracy", "Post2022",
"TradeChina", "PolStab", "FSI"
)) %>%
mutate(
Outcome = ifelse(
grepl("UNGA", Model),
"UNGA Position Index",
"ISEAS Elite Preference"
),
Method = ifelse(
grepl("Country FE", Model),
"Country FE", "OLS"
),
Variable = factor(
term,
levels = rev(c(
"Democracy", "Post2022",
"TradeChina", "PolStab", "FSI"
)),
labels = rev(c(
"Democracy", "Post-2022",
"Trade with China",
"Political Stability", "State Capacity"
))
)
)
# 繪圖
p_robust <- ggplot(
robust_data,
aes(
x = estimate,
y = Variable,
shape = Method,
colour = Method
)
) +
geom_vline(
xintercept = 0,
linetype = "dashed",
colour = "gray65"
) +
geom_errorbar(
aes(xmin = conf.low, xmax = conf.high),
orientation = "y",
position = position_dodge(width = 0.55),
width = 0.2,
linewidth = 0.7
) +
geom_point(
position = position_dodge(width = 0.55),
size = 2.8
) +
facet_wrap(
~ Outcome,
scales = "free_x",
nrow = 1
) +
scale_colour_manual(
values = c("OLS" = "gray55", "Country FE" = "black")
) +
scale_shape_manual(
values = c("OLS" = 16, "Country FE" = 17)
) +
labs(
title = "Robustness Check: OLS vs. Country Fixed Effects",
subtitle = "Coefficient Estimates with 95% Confidence Intervals",
x = "Coefficient Estimate",
y = NULL,
colour = NULL,
shape = NULL
) +
theme_classic(base_size = 14) +
theme(
plot.title = element_text(face = "bold", size = 18),
plot.subtitle = element_text(colour = "gray40"),
strip.text = element_text(face = "bold"),
legend.position = "bottom",
axis.text.y = element_text(size = 11)
)
print(p_robust)

# 儲存圖片
ggsave(
"~/Desktop/wh/ASEAN_Robustness_OLS_vs_FE.png",
p_robust,
width = 12,
height = 6.5,
dpi = 300,
bg = "white"
)
# =========================================
# Change in Relative Position Before/After 2022
# =========================================
library(dplyr)
library(tidyr)
library(ggplot2)
# 1. 計算各國兩個時期的 UNGA 平均值
change_data <- d %>%
filter(!is.na(UNGA)) %>%
mutate(
Period = ifelse(
Year >= 2022,
"Post-2022",
"Pre-2022"
),
Country = as.character(Country),
Country = trimws(Country),
Country = ifelse(
Country == "Lao PDR", "Laos", Country
)
) %>%
group_by(Country, Period) %>%
summarise(
Mean_UNGA = mean(UNGA, na.rm = TRUE),
.groups = "drop"
) %>%
pivot_wider(
names_from = Period,
values_from = Mean_UNGA
) %>%
mutate(
Change = `Post-2022` - `Pre-2022`,
Country = reorder(Country, Change)
)
# 確認八國平均值
print(change_data)
## # A tibble: 8 × 4
## Country `Post-2022` `Pre-2022` Change
## <fct> <dbl> <dbl> <dbl>
## 1 Cambodia 0.736 1.25 -0.510
## 2 Indonesia 0.810 1.24 -0.430
## 3 Laos 0.870 1.28 -0.406
## 4 Malaysia 0.764 1.11 -0.343
## 5 Philippines 0.565 0.962 -0.397
## 6 Singapore 0.570 0.963 -0.393
## 7 Thailand 0.629 0.917 -0.288
## 8 Vietnam 0.838 1.30 -0.461
# 2. 繪製前後比較圖
p_change <- ggplot(change_data, aes(y = Country)) +
# 連接兩個時期的平均值
geom_segment(
aes(
x = `Pre-2022`,
xend = `Post-2022`,
yend = Country
),
color = "gray30",
linewidth = 0.9
) +
# Pre-2022:三角形
geom_point(
aes(x = `Pre-2022`, shape = "Pre-2022"),
size = 3.5,
color = "black"
) +
# Post-2022:圓點
geom_point(
aes(x = `Post-2022`, shape = "Post-2022"),
size = 3.5,
color = "black"
) +
scale_shape_manual(
values = c(
"Pre-2022" = 17,
"Post-2022" = 16
),
breaks = c("Post-2022", "Pre-2022")
) +
labs(
title = "Change in Relative Position Before and After 2022",
subtitle = "Average UNGA Position Index across ASEAN-8, 2010–2024",
x = "Average Relative Position Index",
y = NULL,
shape = "Period",
caption = paste(
"Pre-2022: 2010–2021 |",
"Post-2022: 2022–2024"
)
) +
theme_classic(base_size = 14) +
theme(
plot.title = element_text(
face = "bold",
size = 18
),
plot.subtitle = element_text(
size = 12,
color = "gray40"
),
axis.text.y = element_text(
size = 12,
color = "black"
),
axis.text.x = element_text(
size = 11,
color = "gray30"
),
axis.title.x = element_text(
size = 13
),
legend.position = "bottom",
legend.title = element_blank(),
legend.text = element_text(size = 12),
plot.caption = element_text(
size = 10,
color = "gray45"
),
plot.margin = margin(20, 25, 15, 20)
)
# 3. 顯示圖片
print(p_change)

# 4. 儲存高解析度圖片
ggsave(
"~/Desktop/wh/ASEAN_Change_Pre_Post2022.png",
plot = p_change,
width = 10,
height = 6.5,
dpi = 300,
bg = "white"
)
# =====================================
# Panel Regression: ASEAN-8
# Pooled OLS / Country FE / Random Effects
# =====================================
library(plm)
##
## Attaching package: 'plm'
## The following objects are masked from 'package:dplyr':
##
## between, lag, lead
library(dplyr)
library(lmtest)
library(sandwich)
# 1. 建立 Panel Data
panel_unga <- pdata.frame(
unga_data,
index = c("Country", "Year")
)
panel_iseas <- pdata.frame(
iseas_data,
index = c("Country", "Year")
)
# 2. 設定迴歸公式
formula_panel <- function(y) {
as.formula(paste(
y,
"~ Democracy + SCS + Post2022 +",
"TradeChina + USAlly + PolStab + FSI"
))
}
# =====================================
# UNGA Position Index
# =====================================
# Pooled OLS
pool_unga <- plm(
formula_panel("UNGA"),
data = panel_unga,
model = "pooling"
)
# Country Fixed Effects
fe_unga_panel <- plm(
formula_panel("UNGA"),
data = panel_unga,
model = "within",
effect = "individual"
)
# Random Effects
re_unga <- plm(
formula_panel("UNGA"),
data = panel_unga,
model = "random",
effect = "individual"
)
# =====================================
# ISEAS Elite Preference
# =====================================
pool_iseas <- plm(
formula_panel("ISEAS"),
data = panel_iseas,
model = "pooling"
)
fe_iseas_panel <- plm(
formula_panel("ISEAS"),
data = panel_iseas,
model = "within",
effect = "individual"
)
re_iseas <- plm(
formula_panel("ISEAS"),
data = panel_iseas,
model = "random",
effect = "individual"
)
# =====================================
# 查看結果
# =====================================
summary(pool_unga)
## Pooling Model
##
## Call:
## plm(formula = formula_panel("UNGA"), data = panel_unga, model = "pooling")
##
## Balanced Panel: n = 8, T = 15, N = 120
##
## Residuals:
## Min. 1st Qu. Median 3rd Qu. Max.
## -0.393782 -0.109705 -0.004517 0.120269 0.431128
##
## Coefficients:
## Estimate Std. Error t-value Pr(>|t|)
## (Intercept) 1.5403787 0.2368140 6.5046 2.259e-09 ***
## Democracy -0.0242036 0.0156669 -1.5449 0.1252
## SCS 0.0244431 0.0345426 0.7076 0.4807
## Post2022 -0.3846496 0.0423930 -9.0734 4.531e-15 ***
## TradeChina 0.1759482 0.1915101 0.9187 0.3602
## USAlly -0.2746299 0.0582012 -4.7186 6.907e-06 ***
## PolStab -0.0030226 0.0036441 -0.8295 0.4086
## FSI -0.0026084 0.0023987 -1.0874 0.2792
## ---
## Signif. codes: 0 '***' 0.001 '**' 0.01 '*' 0.05 '.' 0.1 ' ' 1
##
## Total Sum of Squares: 8.7287
## Residual Sum of Squares: 3.4834
## R-Squared: 0.60093
## Adj. R-Squared: 0.57598
## F-statistic: 24.0928 on 7 and 112 DF, p-value: < 2.22e-16
summary(fe_unga_panel)
## Oneway (individual) effect Within Model
##
## Call:
## plm(formula = formula_panel("UNGA"), data = panel_unga, effect = "individual",
## model = "within")
##
## Balanced Panel: n = 8, T = 15, N = 120
##
## Residuals:
## Min. 1st Qu. Median 3rd Qu. Max.
## -0.293815 -0.100565 -0.022286 0.102045 0.444196
##
## Coefficients:
## Estimate Std. Error t-value Pr(>|t|)
## Democracy -0.0216439 0.0373381 -0.5797 0.56335
## Post2022 -0.5202450 0.0526847 -9.8747 < 2e-16 ***
## TradeChina 0.3547755 0.2985557 1.1883 0.23734
## PolStab 0.0134369 0.0056180 2.3918 0.01851 *
## FSI 0.0047590 0.0050632 0.9399 0.34938
## ---
## Signif. codes: 0 '***' 0.001 '**' 0.01 '*' 0.05 '.' 0.1 ' ' 1
##
## Total Sum of Squares: 6.3746
## Residual Sum of Squares: 2.8113
## R-Squared: 0.55899
## Adj. R-Squared: 0.50954
## F-statistic: 27.1255 on 5 and 107 DF, p-value: < 2.22e-16
summary(re_unga)
## Oneway (individual) effect Random Effect Model
## (Swamy-Arora's transformation)
##
## Call:
## plm(formula = formula_panel("UNGA"), data = panel_unga, effect = "individual",
## model = "random")
##
## Balanced Panel: n = 8, T = 15, N = 120
##
## Effects:
## var std.dev share
## idiosyncratic 0.02627 0.16209 1
## individual 0.00000 0.00000 0
## theta: 0
##
## Residuals:
## Min. 1st Qu. Median 3rd Qu. Max.
## -0.393782 -0.109705 -0.004517 0.120269 0.431128
##
## Coefficients:
## Estimate Std. Error z-value Pr(>|z|)
## (Intercept) 1.5403787 0.2368140 6.5046 7.790e-11 ***
## Democracy -0.0242036 0.0156669 -1.5449 0.1224
## SCS 0.0244431 0.0345426 0.7076 0.4792
## Post2022 -0.3846496 0.0423930 -9.0734 < 2.2e-16 ***
## TradeChina 0.1759482 0.1915101 0.9187 0.3582
## USAlly -0.2746299 0.0582012 -4.7186 2.374e-06 ***
## PolStab -0.0030226 0.0036441 -0.8295 0.4068
## FSI -0.0026084 0.0023987 -1.0874 0.2768
## ---
## Signif. codes: 0 '***' 0.001 '**' 0.01 '*' 0.05 '.' 0.1 ' ' 1
##
## Total Sum of Squares: 8.7287
## Residual Sum of Squares: 3.4834
## R-Squared: 0.60093
## Adj. R-Squared: 0.57598
## Chisq: 168.65 on 7 DF, p-value: < 2.22e-16
summary(pool_iseas)
## Pooling Model
##
## Call:
## plm(formula = formula_panel("ISEAS"), data = panel_iseas, model = "pooling")
##
## Balanced Panel: n = 8, T = 6, N = 48
##
## Residuals:
## Min. 1st Qu. Median 3rd Qu. Max.
## -27.9045 -12.6454 -3.1519 8.6755 34.6695
##
## Coefficients:
## Estimate Std. Error t-value Pr(>|t|)
## (Intercept) 86.81426 37.47521 2.3166 0.0257323 *
## Democracy -10.43121 2.80673 -3.7165 0.0006179 ***
## SCS 26.53835 5.89625 4.5009 5.719e-05 ***
## Post2022 -5.89667 5.36684 -1.0987 0.2784580
## TradeChina -60.62561 32.41688 -1.8702 0.0687885 .
## USAlly 10.95056 8.42026 1.3005 0.2008722
## PolStab -0.15222 0.56195 -0.2709 0.7878806
## FSI 0.40399 0.38875 1.0392 0.3049455
## ---
## Signif. codes: 0 '***' 0.001 '**' 0.01 '*' 0.05 '.' 0.1 ' ' 1
##
## Total Sum of Squares: 25827
## Residual Sum of Squares: 13377
## R-Squared: 0.48203
## Adj. R-Squared: 0.39139
## F-statistic: 5.31785 on 7 and 40 DF, p-value: 0.00023511
summary(fe_iseas_panel)
## Oneway (individual) effect Within Model
##
## Call:
## plm(formula = formula_panel("ISEAS"), data = panel_iseas, effect = "individual",
## model = "within")
##
## Balanced Panel: n = 8, T = 6, N = 48
##
## Residuals:
## Min. 1st Qu. Median 3rd Qu. Max.
## -39.8742 -8.6318 -1.1209 9.1223 31.9531
##
## Coefficients:
## Estimate Std. Error t-value Pr(>|t|)
## Democracy -9.874362 18.932656 -0.5216 0.6053
## Post2022 -9.957852 8.475335 -1.1749 0.2480
## TradeChina 3.249719 53.835588 0.0604 0.9522
## PolStab -0.066565 1.678137 -0.0397 0.9686
## FSI 1.043316 1.904118 0.5479 0.5872
##
## Total Sum of Squares: 10830
## Residual Sum of Squares: 10004
## R-Squared: 0.076291
## Adj. R-Squared: -0.24041
## F-statistic: 0.578148 on 5 and 35 DF, p-value: 0.71634
summary(re_iseas)
## Oneway (individual) effect Random Effect Model
## (Swamy-Arora's transformation)
##
## Call:
## plm(formula = formula_panel("ISEAS"), data = panel_iseas, effect = "individual",
## model = "random")
##
## Balanced Panel: n = 8, T = 6, N = 48
##
## Effects:
## var std.dev share
## idiosyncratic 285.82 16.91 0.415
## individual 403.62 20.09 0.585
## theta: 0.6751
##
## Residuals:
## Min. 1st Qu. Median 3rd Qu. Max.
## -34.2206 -8.4899 -2.1782 9.5185 32.4468
##
## Coefficients:
## Estimate Std. Error z-value Pr(>|z|)
## (Intercept) 79.13036 71.72685 1.1032 0.26993
## Democracy -9.49836 5.53676 -1.7155 0.08625 .
## SCS 24.32131 15.50322 1.5688 0.11670
## Post2022 -7.18624 5.07910 -1.4149 0.15711
## TradeChina -15.31922 46.10818 -0.3322 0.73970
## USAlly 14.04434 22.10645 0.6353 0.52523
## PolStab -0.31178 1.06403 -0.2930 0.76951
## FSI 0.48946 0.75162 0.6512 0.51491
## ---
## Signif. codes: 0 '***' 0.001 '**' 0.01 '*' 0.05 '.' 0.1 ' ' 1
##
## Total Sum of Squares: 12413
## Residual Sum of Squares: 10515
## R-Squared: 0.15294
## Adj. R-Squared: 0.0047001
## Chisq: 7.22195 on 7 DF, p-value: 0.40614
# =====================================
# Panel Regression Table
# =====================================
library(modelsummary)
panel_models <- list(
"UNGA Pooled" = pool_unga,
"UNGA FE" = fe_unga_panel,
"UNGA RE" = re_unga,
"ISEAS Pooled" = pool_iseas,
"ISEAS FE" = fe_iseas_panel,
"ISEAS RE" = re_iseas
)
# 使用按國家叢集的穩健共變異數矩陣
panel_vcov <- lapply(
panel_models,
function(m) {
plm::vcovHC(
m,
method = "arellano",
type = "HC1",
cluster = "group"
)
}
)
coef_map <- c(
"Democracy" = "Democracy",
"SCS" = "SCS Claimant",
"Post2022" = "Post-2022",
"TradeChina" = "Trade with China",
"USAlly" = "U.S. Formal Defense Ally",
"PolStab" = "Political Stability",
"FSI" = "State Capacity"
)
modelsummary(
panel_models,
vcov = panel_vcov,
coef_map = coef_map,
statistic = "({std.error})",
estimate = "{estimate}{stars}",
stars = c(
"*" = 0.10,
"**" = 0.05,
"***" = 0.01
),
fmt = 3,
output = "gt"
)
| |
UNGA Pooled |
UNGA FE |
UNGA RE |
ISEAS Pooled |
ISEAS FE |
ISEAS RE |
| Democracy |
-0.024** |
-0.022 |
-0.024** |
-10.431*** |
-9.874 |
-9.498** |
|
(0.010) |
(0.033) |
(0.010) |
(2.938) |
(18.076) |
(4.224) |
| SCS Claimant |
0.024 |
|
0.024 |
26.538*** |
|
24.321*** |
|
(0.023) |
|
(0.023) |
(7.315) |
|
(7.197) |
| Post-2022 |
-0.385*** |
-0.520*** |
-0.385*** |
-5.897 |
-9.958 |
-7.186 |
|
(0.041) |
(0.059) |
(0.041) |
(4.681) |
(7.968) |
(4.580) |
| Trade with China |
0.176 |
0.355 |
0.176 |
-60.626* |
3.250 |
-15.319 |
|
(0.129) |
(0.246) |
(0.129) |
(35.504) |
(52.416) |
(37.521) |
| U.S. Formal Defense Ally |
-0.275*** |
|
-0.275*** |
10.951 |
|
14.044 |
|
(0.071) |
|
(0.071) |
(10.546) |
|
(14.183) |
| Political Stability |
-0.003 |
0.013*** |
-0.003 |
-0.152 |
-0.067 |
-0.312 |
|
(0.004) |
(0.004) |
(0.004) |
(0.428) |
(1.596) |
(0.866) |
| State Capacity |
-0.003 |
0.005 |
-0.003 |
0.404 |
1.043 |
0.489 |
|
(0.003) |
(0.004) |
(0.003) |
(0.362) |
(2.213) |
(0.599) |
| Num.Obs. |
120 |
120 |
120 |
48 |
48 |
48 |
| R2 |
0.601 |
0.559 |
0.601 |
0.482 |
0.076 |
0.153 |
| R2 Adj. |
0.576 |
0.510 |
0.576 |
0.391 |
-0.240 |
0.005 |
| AIC |
-66.2 |
-97.9 |
-66.2 |
424.5 |
404.5 |
412.9 |
| BIC |
-41.1 |
-81.2 |
-41.1 |
441.3 |
415.7 |
429.7 |
| RMSE |
0.17 |
0.15 |
0.17 |
16.69 |
14.44 |
14.80 |
| Std.Errors |
UNGA Pooled |
UNGA FE |
UNGA RE |
ISEAS Pooled |
ISEAS FE |
ISEAS RE |
# =====================================
# Panel Model Selection Tests
# =====================================
# 1. Pooling vs Country FE
plm::pFtest(fe_unga_panel, pool_unga)
##
## F test for individual effects
##
## data: formula_panel("UNGA")
## F = 5.1165, df1 = 5, df2 = 107, p-value = 0.0003021
## alternative hypothesis: significant effects
plm::pFtest(fe_iseas_panel, pool_iseas)
##
## F test for individual effects
##
## data: formula_panel("ISEAS")
## F = 2.3607, df1 = 5, df2 = 35, p-value = 0.06015
## alternative hypothesis: significant effects
# 2. Country FE vs Random Effects
plm::phtest(fe_unga_panel, re_unga)
##
## Hausman Test
##
## data: formula_panel("UNGA")
## chisq = 28.008, df = 5, p-value = 3.626e-05
## alternative hypothesis: one model is inconsistent
plm::phtest(fe_iseas_panel, re_iseas)
##
## Hausman Test
##
## data: formula_panel("ISEAS")
## chisq = 0.63812, df = 5, p-value = 0.9862
## alternative hypothesis: one model is inconsistent
# =====================================
# Sample Period Sensitivity Analysis
# =====================================
library(dplyr)
# 舊版年份
old_sample <- unga_data %>%
filter(Year >= 2014, Year <= 2023)
# 加入2010–2013
extended_sample <- unga_data %>%
filter(Year <= 2023)
# 完整新版
full_sample <- unga_data
formula_test <- UNGA ~
Democracy + SCS + Post2022 +
TradeChina + USAlly + PolStab + FSI
# 三組相同規格的迴歸
old_model <- lm(formula_test, data = old_sample)
extended_model <- lm(
formula_test, data = extended_sample
)
full_model <- lm(
formula_test, data = full_sample
)
# 比較係數
modelsummary::modelsummary(
list(
"2014-2023" = old_model,
"2010-2023" = extended_model,
"2010-2024" = full_model
),
vcov = list(
sandwich::vcovCL(
old_model, cluster = old_sample$Country, type = "HC1"
),
sandwich::vcovCL(
extended_model, cluster = extended_sample$Country, type = "HC1"
),
sandwich::vcovCL(
full_model, cluster = full_sample$Country, type = "HC1"
)
),
statistic = "({std.error})",
stars = TRUE,
output = "gt"
)
| |
2014-2023 |
2010-2023 |
2010-2024 |
| (Intercept) |
1.752*** |
1.545*** |
1.540*** |
|
(0.188) |
(0.320) |
(0.289) |
| Democracy |
-0.028* |
-0.026* |
-0.024* |
|
(0.012) |
(0.013) |
(0.011) |
| SCS |
0.010 |
0.027 |
0.024 |
|
(0.017) |
(0.026) |
(0.025) |
| Post2022 |
-0.457*** |
-0.417*** |
-0.385*** |
|
(0.042) |
(0.044) |
(0.043) |
| TradeChina |
-0.156* |
0.196 |
0.176 |
|
(0.062) |
(0.152) |
(0.137) |
| USAlly |
-0.328*** |
-0.277** |
-0.275*** |
|
(0.025) |
(0.083) |
(0.076) |
| PolStab |
-0.003 |
-0.003 |
-0.003 |
|
(0.003) |
(0.005) |
(0.005) |
| FSI |
-0.003+ |
-0.003 |
-0.003 |
|
(0.002) |
(0.003) |
(0.003) |
| Num.Obs. |
80 |
112 |
120 |
| R2 |
0.708 |
0.579 |
0.601 |
| R2 Adj. |
0.680 |
0.551 |
0.576 |
| AIC |
-50.3 |
-56.2 |
-66.2 |
| BIC |
-28.8 |
-31.7 |
-41.1 |
| Log.Lik. |
34.136 |
37.086 |
42.096 |
| RMSE |
0.16 |
0.17 |
0.17 |
| Std.Errors |
Custom |
Custom |
Custom |
| + p < 0.1, * p < 0.05, ** p < 0.01, *** p < 0.001 |
# =====================================
# Academic Panel Regression Table
# =====================================
library(modelsummary)
library(gt)
## Warning: package 'gt' was built under R version 4.5.2
library(plm)
# 1. 六組 Panel Models
models_table <- list(
"UNGA OLS" = pool_unga,
"UNGA FE" = fe_unga_panel,
"UNGA RE" = re_unga,
"ISEAS OLS" = pool_iseas,
"ISEAS FE" = fe_iseas_panel,
"ISEAS RE" = re_iseas
)
# 2. Country-clustered standard errors
vcovs <- lapply(models_table, function(m) {
plm::vcovHC(
m,
method = "arellano",
type = "HC1",
cluster = "group"
)
})
# 3. Variable names
coef_map <- c(
"Democracy" = "Democracy",
"SCS" = "SCS Claimant",
"Post2022" = "Post-2022",
"TradeChina" = "Trade with China",
"USAlly" = "U.S. Defense Ally",
"PolStab" = "Political Stability",
"FSI" = "State Capacity"
)
# 4. Academic Regression Table
tab_panel <- modelsummary(
models_table,
vcov = vcovs,
coef_map = coef_map,
estimate = "{estimate}{stars}",
statistic = "({std.error})",
stars = c(
"*" = 0.10,
"**" = 0.05,
"***" = 0.01
),
fmt = 3,
output = "gt"
)
# 5. Academic-style formatting
tab_panel <- tab_panel %>%
gt::tab_header(
title = "Panel Regression Results",
subtitle = "ASEAN-8, 2010–2024 / 2019–2024"
) %>%
gt::tab_options(
table.font.size = 13,
table.width = gt::pct(100),
column_labels.font.weight = "bold",
table.border.top.color = "black",
table.border.bottom.color = "black",
data_row.padding = gt::px(6)
) %>%
gt::tab_source_note(
gt::md(
"Country-clustered HC1 standard errors in parentheses. * p < 0.10, ** p < 0.05, *** p < 0.01."
)
)
# 6. Display
tab_panel
| Panel Regression Results |
| ASEAN-8, 2010–2024 / 2019–2024 |
| |
UNGA OLS |
UNGA FE |
UNGA RE |
ISEAS OLS |
ISEAS FE |
ISEAS RE |
| Democracy |
-0.024** |
-0.022 |
-0.024** |
-10.431*** |
-9.874 |
-9.498** |
|
(0.010) |
(0.033) |
(0.010) |
(2.938) |
(18.076) |
(4.224) |
| SCS Claimant |
0.024 |
|
0.024 |
26.538*** |
|
24.321*** |
|
(0.023) |
|
(0.023) |
(7.315) |
|
(7.197) |
| Post-2022 |
-0.385*** |
-0.520*** |
-0.385*** |
-5.897 |
-9.958 |
-7.186 |
|
(0.041) |
(0.059) |
(0.041) |
(4.681) |
(7.968) |
(4.580) |
| Trade with China |
0.176 |
0.355 |
0.176 |
-60.626* |
3.250 |
-15.319 |
|
(0.129) |
(0.246) |
(0.129) |
(35.504) |
(52.416) |
(37.521) |
| U.S. Defense Ally |
-0.275*** |
|
-0.275*** |
10.951 |
|
14.044 |
|
(0.071) |
|
(0.071) |
(10.546) |
|
(14.183) |
| Political Stability |
-0.003 |
0.013*** |
-0.003 |
-0.152 |
-0.067 |
-0.312 |
|
(0.004) |
(0.004) |
(0.004) |
(0.428) |
(1.596) |
(0.866) |
| State Capacity |
-0.003 |
0.005 |
-0.003 |
0.404 |
1.043 |
0.489 |
|
(0.003) |
(0.004) |
(0.003) |
(0.362) |
(2.213) |
(0.599) |
| Num.Obs. |
120 |
120 |
120 |
48 |
48 |
48 |
| R2 |
0.601 |
0.559 |
0.601 |
0.482 |
0.076 |
0.153 |
| R2 Adj. |
0.576 |
0.510 |
0.576 |
0.391 |
-0.240 |
0.005 |
| AIC |
-66.2 |
-97.9 |
-66.2 |
424.5 |
404.5 |
412.9 |
| BIC |
-41.1 |
-81.2 |
-41.1 |
441.3 |
415.7 |
429.7 |
| RMSE |
0.17 |
0.15 |
0.17 |
16.69 |
14.44 |
14.80 |
| Std.Errors |
UNGA OLS |
UNGA FE |
UNGA RE |
ISEAS OLS |
ISEAS FE |
ISEAS RE |
| Country-clustered HC1 standard errors in parentheses. * p < 0.10, ** p < 0.05, *** p < 0.01. |
# 7. Save
gt::gtsave(
tab_panel,
"~/Desktop/wh/ASEAN_Panel_Regression.html"
)
# =====================================
# Complete Panel Regression Table
# =====================================
library(modelsummary)
library(gt)
library(plm)
# 六組模型
models_table <- list(
"UNGA OLS" = pool_unga,
"UNGA FE" = fe_unga_panel,
"UNGA RE" = re_unga,
"ISEAS OLS" = pool_iseas,
"ISEAS FE" = fe_iseas_panel,
"ISEAS RE" = re_iseas
)
# 國家叢集標準誤
vcovs <- lapply(models_table, function(m) {
plm::vcovHC(
m,
method = "arellano",
type = "HC1",
cluster = "group"
)
})
# 完整變數名稱及排列順序
coef_map <- c(
"Democracy" = "Democracy",
"SCS" = "SCS Claimant",
"Post2022" = "Post-2022",
"TradeChina" = "Trade with China",
"USAlly" = "U.S. Formal Defense Ally",
"PolStab" = "Political Stability",
"FSI" = "State Capacity (100 - FSI)",
"(Intercept)" = "Constant"
)
# 模型統計資訊
gof_map <- data.frame(
raw = c("nobs", "r.squared", "adj.r.squared"),
clean = c("Observations", "R-squared", "Adjusted R-squared"),
fmt = c(0, 3, 3)
)
# 產生完整回歸表
tab_panel <- modelsummary(
models_table,
vcov = vcovs,
coef_map = coef_map,
gof_map = gof_map,
estimate = "{estimate}{stars}",
statistic = "({std.error})",
stars = c(
"*" = 0.10,
"**" = 0.05,
"***" = 0.01
),
fmt = 3,
output = "gt"
)
# 美化
tab_panel <- tab_panel |>
gt::tab_header(
title = "Panel Regression Results",
subtitle = "ASEAN-8: UNGA and ISEAS"
) |>
gt::tab_options(
table.font.size = 13,
table.width = gt::pct(100),
column_labels.font.weight = "bold",
table.border.top.color = "black",
table.border.bottom.color = "black",
data_row.padding = gt::px(7)
) |>
gt::tab_source_note(
gt::md(
"Country-clustered HC1 standard errors in parentheses. * p < 0.10, ** p < 0.05, *** p < 0.01."
)
) |>
gt::tab_source_note(
gt::md(
"SCS and U.S. alliance status are absorbed by country fixed effects."
)
)
# 顯示表格
tab_panel
| Panel Regression Results |
| ASEAN-8: UNGA and ISEAS |
| |
UNGA OLS |
UNGA FE |
UNGA RE |
ISEAS OLS |
ISEAS FE |
ISEAS RE |
| Democracy |
-0.024** |
-0.022 |
-0.024** |
-10.431*** |
-9.874 |
-9.498** |
|
(0.010) |
(0.033) |
(0.010) |
(2.938) |
(18.076) |
(4.224) |
| SCS Claimant |
0.024 |
|
0.024 |
26.538*** |
|
24.321*** |
|
(0.023) |
|
(0.023) |
(7.315) |
|
(7.197) |
| Post-2022 |
-0.385*** |
-0.520*** |
-0.385*** |
-5.897 |
-9.958 |
-7.186 |
|
(0.041) |
(0.059) |
(0.041) |
(4.681) |
(7.968) |
(4.580) |
| Trade with China |
0.176 |
0.355 |
0.176 |
-60.626* |
3.250 |
-15.319 |
|
(0.129) |
(0.246) |
(0.129) |
(35.504) |
(52.416) |
(37.521) |
| U.S. Formal Defense Ally |
-0.275*** |
|
-0.275*** |
10.951 |
|
14.044 |
|
(0.071) |
|
(0.071) |
(10.546) |
|
(14.183) |
| Political Stability |
-0.003 |
0.013*** |
-0.003 |
-0.152 |
-0.067 |
-0.312 |
|
(0.004) |
(0.004) |
(0.004) |
(0.428) |
(1.596) |
(0.866) |
| State Capacity (100 - FSI) |
-0.003 |
0.005 |
-0.003 |
0.404 |
1.043 |
0.489 |
|
(0.003) |
(0.004) |
(0.003) |
(0.362) |
(2.213) |
(0.599) |
| Constant |
1.540*** |
|
1.540*** |
86.814*** |
|
79.130 |
|
(0.272) |
|
(0.272) |
(31.132) |
|
(61.613) |
| Observations |
120 |
120 |
120 |
48 |
48 |
48 |
| R-squared |
0.601 |
0.559 |
0.601 |
0.482 |
0.076 |
0.153 |
| Adjusted R-squared |
0.576 |
0.510 |
0.576 |
0.391 |
-0.240 |
0.005 |
| Country-clustered HC1 standard errors in parentheses. * p < 0.10, ** p < 0.05, *** p < 0.01. |
| SCS and U.S. alliance status are absorbed by country fixed effects. |
# 儲存 HTML
gt::gtsave(
tab_panel,
"~/Desktop/wh/ASEAN_Panel_Regression_Complete.html"
)
# ============================================================
# ASEAN Multicollinearity Analysis (VIF)
# Data: Asean1029.xlsx
# ============================================================
# 1. 安裝與載入套件
packages <- c("readxl", "dplyr", "car", "tidyr")
for (p in packages) {
if (!requireNamespace(p, quietly = TRUE)) {
install.packages(p)
}
}
library(readxl)
library(dplyr)
library(car)
## Loading required package: carData
##
## Attaching package: 'car'
## The following object is masked from 'package:dplyr':
##
## recode
library(tidyr)
# 2. 讀取資料
# 如果檔案不在此位置,請修改路徑
file_path <- "~/Desktop/wh/Asean1029.xlsx"
raw <- read_excel(file_path, .name_repair = "unique")
## New names:
## • `Trade China GDP ratio old` -> `Trade China GDP ratio old...13`
## • `Trade China GDP ratio old` -> `Trade China GDP ratio old...14`
# 檢查原始欄位
print(names(raw))
## [1] "Country" "ISO3"
## [3] "Year" "UNGA Normalized Gap"
## [5] "UNGA Position Index" "ISEAS Elite preference"
## [7] "Political Stability" "FSI (100 - raw FSI)"
## [9] "Democracy EIU" "Post2022"
## [11] "SCS" "US Formal Defense Ally (1/0)"
## [13] "Trade China GDP ratio old...13" "Trade China GDP ratio old...14"
# 3. 整理變數
# 依照 Asean1029.xlsx 的欄位位置
d <- data.frame(
Country = as.character(raw[[1]]),
Year = as.integer(raw[[3]]),
UNGA = as.numeric(raw[[5]]),
ISEAS = as.numeric(raw[[6]]),
PolStab = as.numeric(raw[[7]]),
FSI = as.numeric(raw[[8]]),
Democracy = as.numeric(raw[[9]]),
Post2022 = as.numeric(raw[[10]]),
SCS = as.numeric(raw[[11]]),
USAlly = as.numeric(raw[[12]]),
TradeChina = as.numeric(raw[[14]])
)
# 4. 設定三組模型
# Core Model:核心解釋變數
core_vars <- c(
"Democracy",
"SCS",
"Post2022"
)
# Main Model:核心變數 + 主要控制變數
main_vars <- c(
core_vars,
"TradeChina",
"USAlly"
)
# Full Model:加入政治穩定與 FSI
full_vars <- c(
main_vars,
"PolStab",
"FSI"
)
# 5. 建立 VIF 計算函數
run_vif <- function(data, dv, vars, model_name) {
# 使用該模型所有變數皆非缺失的樣本
model_data <- data %>%
select(all_of(c(dv, vars))) %>%
drop_na()
# 建立迴歸公式
formula <- as.formula(
paste(dv, "~", paste(vars, collapse = " + "))
)
# 執行 OLS
model <- lm(formula, data = model_data)
# 計算 VIF
vif_values <- car::vif(model)
# 整理結果
result <- data.frame(
DV = dv,
Model = model_name,
Variable = names(vif_values),
VIF = as.numeric(vif_values),
Tolerance = 1 / as.numeric(vif_values),
N = nrow(model_data)
)
return(result)
}
# 6. UNGA 三組模型
vif_unga_core <- run_vif(
d, "UNGA", core_vars, "Core"
)
vif_unga_main <- run_vif(
d, "UNGA", main_vars, "Main"
)
vif_unga_full <- run_vif(
d, "UNGA", full_vars, "Full"
)
# 7. ISEAS 三組模型
vif_iseas_core <- run_vif(
d, "ISEAS", core_vars, "Core"
)
vif_iseas_main <- run_vif(
d, "ISEAS", main_vars, "Main"
)
vif_iseas_full <- run_vif(
d, "ISEAS", full_vars, "Full"
)
# 8. 合併所有結果
vif_results <- bind_rows(
vif_unga_core,
vif_unga_main,
vif_unga_full,
vif_iseas_core,
vif_iseas_main,
vif_iseas_full
)
# 9. 顯示完整結果
print(vif_results, row.names = FALSE)
## DV Model Variable VIF Tolerance N
## UNGA Core Democracy 1.022160 0.9783199 120
## UNGA Core SCS 1.021898 0.9785717 120
## UNGA Core Post2022 1.000263 0.9997371 120
## UNGA Main Democracy 1.306630 0.7653279 120
## UNGA Main SCS 1.049774 0.9525857 120
## UNGA Main Post2022 1.086184 0.9206546 120
## UNGA Main TradeChina 1.443607 0.6927094 120
## UNGA Main USAlly 1.285045 0.7781827 120
## UNGA Full Democracy 2.998901 0.3334555 120
## UNGA Full SCS 1.078995 0.9267884 120
## UNGA Full Post2022 1.109441 0.9013544 120
## UNGA Full TradeChina 1.868316 0.5352412 120
## UNGA Full USAlly 2.450540 0.4080733 120
## UNGA Full PolStab 8.085307 0.1236811 120
## UNGA Full FSI 6.385131 0.1566139 120
## ISEAS Core Democracy 1.037861 0.9635197 48
## ISEAS Core SCS 1.037859 0.9635221 48
## ISEAS Core Post2022 1.000003 0.9999974 48
## ISEAS Main Democracy 1.866237 0.5358377 48
## ISEAS Main SCS 1.114936 0.8969128 48
## ISEAS Main Post2022 1.027513 0.9732239 48
## ISEAS Main TradeChina 2.032861 0.4919175 48
## ISEAS Main USAlly 1.353799 0.7386622 48
## ISEAS Full Democracy 4.448845 0.2247774 48
## ISEAS Full SCS 1.169485 0.8550776 48
## ISEAS Full Post2022 1.033495 0.9675909 48
## ISEAS Full TradeChina 2.268942 0.4407341 48
## ISEAS Full USAlly 1.908023 0.5241027 48
## ISEAS Full PolStab 6.194522 0.1614330 48
## ISEAS Full FSI 6.045584 0.1654100 48
# 10. 製作適合論文的 VIF 比較表
vif_table <- vif_results %>%
mutate(
Model = paste(DV, Model, sep = "_"),
VIF = round(VIF, 3)
) %>%
select(Variable, Model, VIF) %>%
pivot_wider(
names_from = Model,
values_from = VIF
)
print(vif_table, width = Inf)
## # A tibble: 7 × 7
## Variable UNGA_Core UNGA_Main UNGA_Full ISEAS_Core ISEAS_Main ISEAS_Full
## <chr> <dbl> <dbl> <dbl> <dbl> <dbl> <dbl>
## 1 Democracy 1.02 1.31 3.00 1.04 1.87 4.45
## 2 SCS 1.02 1.05 1.08 1.04 1.12 1.17
## 3 Post2022 1 1.09 1.11 1 1.03 1.03
## 4 TradeChina NA 1.44 1.87 NA 2.03 2.27
## 5 USAlly NA 1.28 2.45 NA 1.35 1.91
## 6 PolStab NA NA 8.09 NA NA 6.20
## 7 FSI NA NA 6.38 NA NA 6.05
# 11. 匯出 CSV
write.csv(
vif_results,
"ASEAN_VIF_Results.csv",
row.names = FALSE
)
write.csv(
vif_table,
"ASEAN_VIF_Table.csv",
row.names = FALSE
)