284 lines
9.2 KiB
R
284 lines
9.2 KiB
R
# Mixed ANOVA Analysis for Past vs Future Differences
|
|
# EOHI Experiment Data Analysis
|
|
|
|
# Load required libraries
|
|
library(tidyverse)
|
|
library(ez)
|
|
library(afex)
|
|
library(emmeans)
|
|
library(ggplot2)
|
|
library(car)
|
|
|
|
# Read the data
|
|
data <- read.csv("eohi1/exp1.csv")
|
|
|
|
# Display basic information about the dataset
|
|
cat("Dataset dimensions:", dim(data), "\n")
|
|
cat("Number of participants:", length(unique(data$pID)), "\n")
|
|
|
|
# Check experimental conditions
|
|
cat("\nExperimental conditions:\n")
|
|
table(data$GROUP, data$TASK_DO, data$TEMPORAL_DO)
|
|
|
|
# Prepare data for mixed ANOVA
|
|
# We'll reshape the data to have Past and Future as separate rows for each participant
|
|
|
|
# Create a function to reshape data for a specific domain
|
|
reshape_domain_data <- function(data, domain_name) {
|
|
past_col <- paste0("NPastDiff_", domain_name)
|
|
fut_col <- paste0("NFutDiff_", domain_name)
|
|
|
|
# Check if columns exist
|
|
if (!(past_col %in% colnames(data)) || !(fut_col %in% colnames(data))) {
|
|
cat("Warning: Columns", past_col, "or", fut_col, "not found\n")
|
|
return(NULL)
|
|
}
|
|
|
|
# Create long format data
|
|
past_data <- data %>%
|
|
select(pID, ResponseId, GROUP, TASK_DO, TEMPORAL_DO, ITEM_DO, COC_DO,
|
|
demo_sex, demo_age_1, AOT_total, CRT_correct, all_of(past_col)) %>%
|
|
mutate(TimePerspective = "Past",
|
|
Difference = .data[[past_col]]) %>%
|
|
select(-all_of(past_col))
|
|
|
|
fut_data <- data %>%
|
|
select(pID, ResponseId, GROUP, TASK_DO, TEMPORAL_DO, ITEM_DO, COC_DO,
|
|
demo_sex, demo_age_1, AOT_total, CRT_correct, all_of(fut_col)) %>%
|
|
mutate(TimePerspective = "Future",
|
|
Difference = .data[[fut_col]]) %>%
|
|
select(-all_of(fut_col))
|
|
|
|
combined_data <- rbind(past_data, fut_data) %>%
|
|
mutate(TimePerspective = as.factor(TimePerspective),
|
|
pID = as.factor(pID))
|
|
|
|
return(combined_data)
|
|
}
|
|
|
|
# Define domains to analyze
|
|
domains <- c("pref_read", "pref_music", "pref_tv", "pref_nap", "pref_travel",
|
|
"pers_extravert", "pers_critical", "pers_dependable", "pers_anxious", "pers_complex",
|
|
"val_obey", "val_trad", "val_opinion", "val_performance", "val_justice",
|
|
"life_ideal", "life_excellent", "life_satisfied", "life_important", "life_change")
|
|
|
|
# Run mixed ANOVA for each domain
|
|
results_list <- list()
|
|
|
|
for (domain in domains) {
|
|
cat("\n", "="*60, "\n")
|
|
cat("ANALYZING DOMAIN:", toupper(domain), "\n")
|
|
cat("="*60, "\n")
|
|
|
|
# Reshape data for this domain
|
|
domain_data <- reshape_domain_data(data, domain)
|
|
|
|
if (is.null(domain_data)) {
|
|
next
|
|
}
|
|
|
|
# Check for missing values
|
|
missing_count <- sum(is.na(domain_data$Difference))
|
|
if (missing_count > 0) {
|
|
cat("Warning:", missing_count, "missing values found for", domain, "\n")
|
|
domain_data <- domain_data[!is.na(domain_data$Difference), ]
|
|
}
|
|
|
|
# Descriptive statistics
|
|
cat("\nDescriptive Statistics:\n")
|
|
desc_stats <- domain_data %>%
|
|
group_by(TimePerspective) %>%
|
|
summarise(
|
|
n = n(),
|
|
mean = mean(Difference, na.rm = TRUE),
|
|
sd = sd(Difference, na.rm = TRUE),
|
|
median = median(Difference, na.rm = TRUE),
|
|
.groups = 'drop'
|
|
)
|
|
print(desc_stats)
|
|
|
|
# Effect size (Cohen's d)
|
|
past_diff <- domain_data$Difference[domain_data$TimePerspective == "Past"]
|
|
fut_diff <- domain_data$Difference[domain_data$TimePerspective == "Future"]
|
|
|
|
pooled_sd <- sqrt(((length(past_diff) - 1) * var(past_diff) +
|
|
(length(fut_diff) - 1) * var(fut_diff)) /
|
|
(length(past_diff) + length(fut_diff) - 2))
|
|
|
|
cohens_d <- (mean(past_diff) - mean(fut_diff)) / pooled_sd
|
|
|
|
cat("\nCohen's d (Past vs Future):", round(cohens_d, 5), "\n")
|
|
|
|
# Mixed ANOVA using ezANOVA
|
|
tryCatch({
|
|
# Simple repeated measures ANOVA (TimePerspective as within-subjects)
|
|
anova_result <- ezANOVA(
|
|
data = domain_data,
|
|
dv = Difference,
|
|
wid = pID,
|
|
within = TimePerspective,
|
|
between = c(GROUP, TASK_DO),
|
|
type = 3,
|
|
detailed = TRUE
|
|
)
|
|
|
|
cat("\nMixed ANOVA Results:\n")
|
|
print(anova_result)
|
|
|
|
# Store results
|
|
results_list[[domain]] <- list(
|
|
descriptive = desc_stats,
|
|
cohens_d = cohens_d,
|
|
anova = anova_result
|
|
)
|
|
|
|
# Post-hoc comparisons if significant
|
|
if (!is.null(anova_result$ANOVA)) {
|
|
if (any(anova_result$ANOVA$p < 0.05, na.rm = TRUE)) {
|
|
cat("\nSignificant effects found! Post-hoc analysis:\n")
|
|
|
|
# Pairwise comparisons for TimePerspective
|
|
if ("TimePerspective" %in% anova_result$ANOVA$Effect &&
|
|
anova_result$ANOVA$p[anova_result$ANOVA$Effect == "TimePerspective"] < 0.05) {
|
|
|
|
# Simple t-test for comparison
|
|
t_test_result <- t.test(past_diff, fut_diff, paired = TRUE)
|
|
cat("\nPaired t-test (Past vs Future):\n")
|
|
cat("t =", round(t_test_result$statistic, 3),
|
|
", df =", t_test_result$parameter,
|
|
", p =", round(t_test_result$p.value, 5), "\n")
|
|
}
|
|
}
|
|
}
|
|
|
|
}, error = function(e) {
|
|
cat("Error in ANOVA for", domain, ":", e$message, "\n")
|
|
|
|
# Fallback to simple paired t-test
|
|
t_test_result <- t.test(past_diff, fut_diff, paired = TRUE)
|
|
cat("\nFallback: Paired t-test (Past vs Future):\n")
|
|
cat("t =", round(t_test_result$statistic, 3),
|
|
", df =", t_test_result$parameter,
|
|
", p =", round(t_test_result$p.value, 5), "\n")
|
|
|
|
results_list[[domain]] <- list(
|
|
descriptive = desc_stats,
|
|
cohens_d = cohens_d,
|
|
t_test = t_test_result
|
|
)
|
|
})
|
|
}
|
|
|
|
# Summary of all results
|
|
cat("\n", "="*80, "\n")
|
|
cat("SUMMARY OF ALL DOMAINS\n")
|
|
cat("="*80, "\n")
|
|
|
|
summary_df <- data.frame(
|
|
Domain = character(),
|
|
Past_Mean = numeric(),
|
|
Future_Mean = numeric(),
|
|
Cohen_d = numeric(),
|
|
Significant = logical(),
|
|
stringsAsFactors = FALSE
|
|
)
|
|
|
|
for (domain in names(results_list)) {
|
|
result <- results_list[[domain]]
|
|
|
|
past_mean <- result$descriptive$mean[result$descriptive$TimePerspective == "Past"]
|
|
fut_mean <- result$descriptive$mean[result$descriptive$TimePerspective == "Future"]
|
|
cohens_d <- result$cohens_d
|
|
|
|
# Check if significant (p < 0.05)
|
|
significant <- FALSE
|
|
if (!is.null(result$anova) && !is.null(result$anova$ANOVA)) {
|
|
if ("TimePerspective" %in% result$anova$ANOVA$Effect) {
|
|
p_val <- result$anova$ANOVA$p[result$anova$ANOVA$Effect == "TimePerspective"]
|
|
significant <- !is.na(p_val) && p_val < 0.05
|
|
}
|
|
} else if (!is.null(result$t_test)) {
|
|
significant <- result$t_test$p.value < 0.05
|
|
}
|
|
|
|
summary_df <- rbind(summary_df, data.frame(
|
|
Domain = domain,
|
|
Past_Mean = round(past_mean, 3),
|
|
Future_Mean = round(fut_mean, 3),
|
|
Cohen_d = round(cohens_d, 5),
|
|
Significant = significant
|
|
))
|
|
}
|
|
|
|
# Sort by effect size (absolute value)
|
|
summary_df <- summary_df[order(abs(summary_df$Cohen_d), decreasing = TRUE), ]
|
|
|
|
print(summary_df)
|
|
|
|
# Create visualization
|
|
library(ggplot2)
|
|
|
|
# Prepare data for plotting
|
|
plot_data <- summary_df %>%
|
|
mutate(
|
|
Effect_Size = abs(Cohen_d),
|
|
Direction = ifelse(Cohen_d > 0, "Past > Future", "Future > Past"),
|
|
Domain_Type = case_when(
|
|
grepl("pref_", Domain) ~ "Preferences",
|
|
grepl("pers_", Domain) ~ "Personality",
|
|
grepl("val_", Domain) ~ "Values",
|
|
grepl("life_", Domain) ~ "Life Satisfaction",
|
|
TRUE ~ "Other"
|
|
)
|
|
)
|
|
|
|
# Effect size plot
|
|
p1 <- ggplot(plot_data, aes(x = reorder(Domain, Effect_Size), y = Effect_Size,
|
|
fill = Direction, alpha = Significant)) +
|
|
geom_col() +
|
|
coord_flip() +
|
|
scale_alpha_manual(values = c(0.5, 1), name = "Significant\n(p < 0.05)") +
|
|
scale_fill_manual(values = c("Past > Future" = "#E74C3C", "Future > Past" = "#3498DB")) +
|
|
labs(
|
|
title = "Effect Sizes: Past vs Future Differences",
|
|
subtitle = "Absolute Cohen's d values across domains",
|
|
x = "Domain",
|
|
y = "|Cohen's d|",
|
|
fill = "Direction"
|
|
) +
|
|
theme_minimal() +
|
|
theme(axis.text.y = element_text(size = 8))
|
|
|
|
print(p1)
|
|
|
|
# Mean differences plot
|
|
plot_data_long <- summary_df %>%
|
|
select(Domain, Past_Mean, Future_Mean) %>%
|
|
pivot_longer(cols = c(Past_Mean, Future_Mean),
|
|
names_to = "TimePerspective",
|
|
values_to = "Mean_Difference") %>%
|
|
mutate(TimePerspective = gsub("_Mean", "", TimePerspective))
|
|
|
|
p2 <- ggplot(plot_data_long, aes(x = reorder(Domain, Mean_Difference),
|
|
y = Mean_Difference,
|
|
fill = TimePerspective)) +
|
|
geom_col(position = "dodge") +
|
|
coord_flip() +
|
|
scale_fill_manual(values = c("Past" = "#E74C3C", "Future" = "#3498DB")) +
|
|
labs(
|
|
title = "Mean Differences by Time Perspective",
|
|
subtitle = "Past vs Future difference scores",
|
|
x = "Domain",
|
|
y = "Mean Difference Score",
|
|
fill = "Time Perspective"
|
|
) +
|
|
theme_minimal() +
|
|
theme(axis.text.y = element_text(size = 8))
|
|
|
|
print(p2)
|
|
|
|
cat("\nAnalysis complete! Check the plots and summary table above.\n")
|
|
cat("Key findings:\n")
|
|
cat("- Domains with largest effect sizes:", paste(head(summary_df$Domain, 3), collapse = ", "), "\n")
|
|
cat("- Number of significant differences:", sum(summary_df$Significant), "out of", nrow(summary_df), "\n")
|