|
| 1 | +################################################################################ |
| 2 | +# DESCRIPTION: Test R's coxme package to perform a Cox proportional hazard model |
| 3 | +# with mixed effects (r.e. on location, not yet available in Python packages) |
| 4 | +# PROJECT: Climate nutrition |
| 5 | +# DATE: 2025-09-16 |
| 6 | +################################################################################ |
| 7 | + |
| 8 | +#============================================================================== |
| 9 | +# SECTION 0: PACKAGE LOADING AND ENVIRONMENT SETUP |
| 10 | +#============================================================================== |
| 11 | +# Clear workspace |
| 12 | +rm(list = ls()) |
| 13 | + |
| 14 | +# Username is pulled automatically |
| 15 | +username <- Sys.info()[["user"]] |
| 16 | +if (Sys.info()["sysname"] == "Linux") { |
| 17 | + j <- "/home/j/" |
| 18 | + h <- paste0("/homes/", username, "/") |
| 19 | + r <- "/mnt/" |
| 20 | + l <-"/ihme/limited_use/" |
| 21 | +} else { |
| 22 | + j <- "J:/" |
| 23 | + h <- "H:/" |
| 24 | + r <- "R:/" |
| 25 | + l <- "L:/" |
| 26 | +} |
| 27 | + |
| 28 | +install.packages('coxme',lib = "/homes/elyeb/rlibs") # for survival analysis with mixed effects |
| 29 | +library(coxme,lib.loc = "/homes/elyeb/rlibs") |
| 30 | +library(data.table) |
| 31 | +library(arrow) # to read parquet |
| 32 | + |
| 33 | +options(scipen = 999) # turn off scientific notation |
| 34 | + |
| 35 | +#============================================================================== |
| 36 | +# SECTION 1: DATA LOADING AND PREPROCESSING |
| 37 | +#============================================================================== |
| 38 | + |
| 39 | +df <- read_parquet("/mnt/team/rapidresponse/pub/population/modeling/climate_malnutrition/child_mortality/training_data/2025_09_15.01/data.parquet") |
| 40 | + |
| 41 | +df <- data.table(df) |
| 42 | + |
| 43 | +# flip child_alive so 1 = died, 0 = alive for easier interpretation |
| 44 | +df[,child_mortality := 1-child_alive] |
| 45 | + |
| 46 | +setnames(df,old="ldipc_weighted_no_match",new="consumption") |
| 47 | + |
| 48 | +df_model <- df[,.(child_mortality,age_month_at_year_end,sex_id,ihme_loc_id,consumption,mean_temperature,days_over_30C)] |
| 49 | + |
| 50 | +#============================================================================== |
| 51 | +# SECTION 2: MAIN PROCESSING |
| 52 | +#============================================================================== |
| 53 | + |
| 54 | +fit <- coxme(Surv(age_month_at_year_end, child_mortality) ~ consumption + mean_temperature + days_over_30C + sex_id + (1|ihme_loc_id), data = df_model) |
| 55 | +summary(fit) |
| 56 | +# Mixed effects coxme model |
| 57 | +# Formula: Surv(age_month_at_year_end, child_mortality) ~ consumption + mean_temperature + days_over_30C + sex_id + (1 | ihme_loc_id) |
| 58 | +# Data: df_model |
| 59 | +# |
| 60 | +# events, n = 42130, 4893786 |
| 61 | +# |
| 62 | +# Random effects: |
| 63 | +# group variable sd variance |
| 64 | +# 1 ihme_loc_id Intercept 1.135688 1.289787 |
| 65 | +# Chisq df p AIC BIC |
| 66 | +# Integrated loglik 16118 5.00 0 16108 16065 |
| 67 | +# Penalized loglik 16241 18.78 0 16204 16041 |
| 68 | +# |
| 69 | +# Fixed effects: |
| 70 | +# coef exp(coef) se(coef) z p |
| 71 | +# consumption -0.000229703 0.999770323 0.000004872 -47.15 <0.0000000000000002 |
| 72 | +# mean_temperature -0.015280408 0.984835745 0.001395616 -10.95 <0.0000000000000002 |
| 73 | +# days_over_30C 0.003450759 1.003456720 0.000152407 22.64 <0.0000000000000002 |
| 74 | +# sex_id -0.017863722 0.982294889 0.009749483 -1.83 0.0669 |
| 75 | + |
0 commit comments