A | B | C | D | E | F | G | H | I | J | K | L | M | N | O | P | Q | R | S | T | U | V | W | X | Y | Z | AA | AB | AC | AD | AE | AF | AG | |
---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|
1 | |||||||||||||||||||||||||||||||||
2 | Author | Chad Milando, PhD, MS | cmilando@bu.edu | Interested in similar spreadsheets? see here: | # R code to reproduce this spreadsheet | ||||||||||||||||||||||||||||
3 | Date | 7.14.2023 | https://chadmilando.com/teaching/ | ||||||||||||||||||||||||||||||
4 | library(dlnm) | ||||||||||||||||||||||||||||||||
5 | Purpose | DLNM in Excel, with no macros (Solver used for Poisson) | library(splines) | ||||||||||||||||||||||||||||||
6 | Recommended view % is 75% | library(tidyverse) | |||||||||||||||||||||||||||||||
7 | library(lubridate) | ||||||||||||||||||||||||||||||||
8 | References | https://onlinelibrary.wiley.com/doi/full/10.1002/sim.5963 | |||||||||||||||||||||||||||||||
9 | https://github.com/gasparrini/dlnm | df <- dlnm::chicagoNMMAPS | |||||||||||||||||||||||||||||||
10 | df2 <- df %>% filter(month %in% 5:9, year == 1990) | ||||||||||||||||||||||||||||||||
11 | Sheets | df2$dow_fct <- paste0('x', wday(df2$date, week_start = 1)) | |||||||||||||||||||||||||||||||
12 | Step 1: getting model coefficients | ||||||||||||||||||||||||||||||||
13 | Chicago data sample | the data | Step 1 | k50 <- quantile(df2$temp, probs = 0.5) | |||||||||||||||||||||||||||||
14 | bs example | an example spreadsheet for the bs() function in R | |||||||||||||||||||||||||||||||
15 | bs | using bs() on the temperature variable | cb1.temp <- dlnm::crossbasis( | ||||||||||||||||||||||||||||||
16 | poly | creating a polynomial basis of the 30-lag | df2$temp, argvar=list(knots = k50, fun = "bs", degree = 3, intercept = F), | ||||||||||||||||||||||||||||||
17 | offset basisvar | offsetting the temperature basis to match the 30day lag | lag = 30, arglag = list(fun="poly", degree = 2, intercept = F)) | ||||||||||||||||||||||||||||||
18 | crossbasis | taking row products of the two bases to create the cross basis | model3 <- glm(death ~ cb1.temp + dow_fct, family=poisson(), df2) | ||||||||||||||||||||||||||||||
19 | Poisson predict | getting model coefficients via unconditional poisson regression | |||||||||||||||||||||||||||||||
20 | |||||||||||||||||||||||||||||||||
21 | Step 2: using model coefficients to make the graphs | Step 2 | pred3.temp <- crosspred(cb1.temp, | ||||||||||||||||||||||||||||||
22 | cen bs | using the bs() from above, convert the center point to basis form | model3, bylag = 1, cumul = T, at = seq(6.5, 30, by = 0.5), cen = 20.5) | ||||||||||||||||||||||||||||||
23 | varvec bs | for the newdata you want to pred on, make basis, center on ^ | |||||||||||||||||||||||||||||||
24 | crosspred | combine varvec bs with varlag bs, which is poly^ in this case | plot(pred3.temp) | ||||||||||||||||||||||||||||||
25 | crosspred output | take different slices to view RR by lag or by temp overall | |||||||||||||||||||||||||||||||
26 | # for temp = 10, what is the RR by lag | ||||||||||||||||||||||||||||||||
27 | Notes | plot(pred3.temp, var = 10, cumul = T, | |||||||||||||||||||||||||||||||
28 | The major first hurdle was replicating the cross-basis function | ylab="Cumulative RR", col = 2) | |||||||||||||||||||||||||||||||
29 | |||||||||||||||||||||||||||||||||
30 | * basically, you use a crossbasis when you want to: | # what is the overall relationship | |||||||||||||||||||||||||||||||
31 | (1) model the relationship between exposure and outcome (non-linearly, independent of time) | plot(pred3.temp, 'overall', col = 2, | |||||||||||||||||||||||||||||||
32 | so, exposure = 50 C-> probabiliy of outcome 0.12, exposure = 40 C -> P(outcome) = 0.4 | ylab="Cumulative RR", xlab="Temperature") | |||||||||||||||||||||||||||||||
33 | (2) model the impact of time (indepedent of exposure level) | ||||||||||||||||||||||||||||||||
34 | your cumulative exposure today is 1 * todays exposure + 0.5 * yesterday's exposure | ||||||||||||||||||||||||||||||||
35 | using cross basis allows you to model both together. you multiply the basis of each together | ||||||||||||||||||||||||||||||||
36 | |||||||||||||||||||||||||||||||||
37 | Note: I ignore the group component for simplicity, so this just assumes 1 strata etc. | ||||||||||||||||||||||||||||||||
38 | but otherwise it’s the same, lags are just put inside each group | ||||||||||||||||||||||||||||||||
39 | |||||||||||||||||||||||||||||||||
40 | On the choice of centering value in crosspred | ||||||||||||||||||||||||||||||||
41 | (from Gasparrini 2013) | ||||||||||||||||||||||||||||||||
42 | Therefore the cross-basis in (7) should always be defined without an intercept in the basis functions for x. Also, these basis functions can be centered on a specific exposure value x0, which will represent the reference for the risk summaries computed by (8)–(10). | ||||||||||||||||||||||||||||||||
43 | |||||||||||||||||||||||||||||||||
44 | The centering value for crosspred doesn't have a statistical interpretation, other than as a reference | ||||||||||||||||||||||||||||||||
45 | Just choose a comparison value that make the interpretation make sense | ||||||||||||||||||||||||||||||||
46 | (mean daily max temperature) | ||||||||||||||||||||||||||||||||
47 | |||||||||||||||||||||||||||||||||
48 | Questions I'm still working on answering | ||||||||||||||||||||||||||||||||
49 | > what is the rationale behind the formula for SE in varvec | ||||||||||||||||||||||||||||||||
50 | |||||||||||||||||||||||||||||||||
51 | |||||||||||||||||||||||||||||||||
52 | |||||||||||||||||||||||||||||||||
53 | |||||||||||||||||||||||||||||||||
54 | |||||||||||||||||||||||||||||||||
55 | |||||||||||||||||||||||||||||||||
56 | |||||||||||||||||||||||||||||||||
57 | |||||||||||||||||||||||||||||||||
58 | |||||||||||||||||||||||||||||||||
59 | |||||||||||||||||||||||||||||||||
60 | |||||||||||||||||||||||||||||||||
61 | |||||||||||||||||||||||||||||||||
62 | |||||||||||||||||||||||||||||||||
63 | |||||||||||||||||||||||||||||||||
64 | |||||||||||||||||||||||||||||||||
65 | |||||||||||||||||||||||||||||||||
66 | |||||||||||||||||||||||||||||||||
67 | |||||||||||||||||||||||||||||||||
68 | |||||||||||||||||||||||||||||||||
69 | |||||||||||||||||||||||||||||||||
70 | |||||||||||||||||||||||||||||||||
71 | |||||||||||||||||||||||||||||||||
72 | |||||||||||||||||||||||||||||||||
73 | |||||||||||||||||||||||||||||||||
74 | |||||||||||||||||||||||||||||||||
75 | |||||||||||||||||||||||||||||||||
76 | |||||||||||||||||||||||||||||||||
77 | |||||||||||||||||||||||||||||||||
78 | |||||||||||||||||||||||||||||||||
79 | |||||||||||||||||||||||||||||||||
80 | |||||||||||||||||||||||||||||||||
81 | |||||||||||||||||||||||||||||||||
82 | |||||||||||||||||||||||||||||||||
83 | |||||||||||||||||||||||||||||||||
84 | |||||||||||||||||||||||||||||||||
85 | |||||||||||||||||||||||||||||||||
86 | |||||||||||||||||||||||||||||||||
87 | |||||||||||||||||||||||||||||||||
88 | |||||||||||||||||||||||||||||||||
89 | |||||||||||||||||||||||||||||||||
90 | |||||||||||||||||||||||||||||||||
91 | |||||||||||||||||||||||||||||||||
92 | |||||||||||||||||||||||||||||||||
93 | |||||||||||||||||||||||||||||||||
94 | |||||||||||||||||||||||||||||||||
95 | |||||||||||||||||||||||||||||||||
96 | |||||||||||||||||||||||||||||||||
97 | |||||||||||||||||||||||||||||||||
98 | |||||||||||||||||||||||||||||||||
99 | |||||||||||||||||||||||||||||||||
100 |