inferference
inferference
This is a brief description of how to use the inferference
package.
# load the package
library(inferference)
I have included a simple dataset generated from rinterferenceSim
package: 3000 units, 250 groups, 2 covariates, 21 allocations (0 to 1 by 0.05), using the parameters in the code below. See Perez 2014 for details on how the simulations were structured.
alphaz = seq(0, 1, by=.05) # needed to compute truth
theta.base <- c(.5, -0.788, -2.953, -0.098, -0.145, 0.351)
theta.sim <- c(0.2727, -0.0387, .2719, 1.0859)
sample_sim <- sim_interference(n = 3000, N = 250, nsims = 1,
base.parameters = theta.base,
parameters = theta.sim,
alphas = alphaz)
interference_sample <- sample_sim$sims[[1]]
#save(sample_data, file = "data/sample_data.rda")
Here’s what the data looks like:
head(vaccinesim)
## y X1 X2 A B group
## 1 1 5.3607 1.716 0 0 1
## 2 0 0.1965 1.731 0 1 1
## 3 0 0.4846 1.770 1 1 1
## 4 0 0.8013 1.716 0 1 1
## 5 0 2.1427 1.772 1 1 1
## 6 0 1.2861 1.716 0 1 1
y is the outcome. X1 and X2 are covariates. A is the randomized treatment indicator. B is an indicator of participation in the trial. Group is obvious.
interference
functionThe primary function in inferference
is interference
. Currently, it only supports IPW estimation. interference
has several options:
propensity_integrand
: a character string that names the function that defines the group-level propensity: \(P(\mathbf{A}_i | \mathbf{X}_i)\). The default function is logit_integrand
. This function handles models with and without random effects. Without random effects, logit_integrand
computes: \[
\prod_{j = 1}^n_i h_{ij}^{A_{ij}}(1 - h_{ij})^{1 - A_{ij}}
\] where \(h_{ij} = logit^{-1}(\mathbf{X}\hat{\theta})\); \(\hat{\theta}\) are the estimated parameters from logistic regression using glm
. In the case of a random effect, logit_integrand
computes: \[
\prod_{j = 1}^n_i h_{ij}(b_i)^{A_{ij}}(1 - h_{ij}(b_i))^{1 - A_{ij}}f_b(b_i)
\] where \(h_{ij} = logit^{-1}(\mathbf{X}\hat{\theta} + b)\); \(\hat{\boldsymbol{\theta}}_f\) are the estimated fixed effect parameters from random effects logistic regression using glmer
; \(f_b(\cdot)\) is a \(N(0, \hat{\theta}_r)\) density; \(\hat{\theta}_r\) is the estimated random effect variance. For both cases logit_integrand
is passed through the integrate
function. Without a random effect, however, this has no effect since integrate(function(b) dnorm(b))
equals 1.outcome | exposure ~ propensity covariates | group
. If a random effect for the group is included use the following:outcome | exposure ~ propensity covariates + (1|group) | group
. If the study design includes a ‘participation’ variable like in Perez-Heydrich 2014 use the following:outcome | exposure | participation ~ propensity covariates + (1|group) | group
.oracle
, glm
, or glmer
.model_method
as a list. For example, for glm
or glmer
set this equal to list(family = binomial(link = 'logit'))
. To use the oracle
method, use list(fixed.effects = c(???, ???, etc), random.effects = NULL)
or list(fixed.effects = c(???, ???, etc), random.effects = ???)
ipw_interference
. list(variance_estimation = 'naive')
or list(variance_estimation = 'robust')
are the option settings of most interest. ‘robust’ is the default. ‘robust’ uses M-estimation theory to compute the variance, whereas, ‘naive’ computes \(\frac{1}{N^2}\sum_{i= 1}^N (\hat{CE}_i - \hat{CE})^2\), where \(\hat{CE}\) is point estimate for the causal effect of interest while \(\hat{CE}_i\) is the point estimate for group \(i\).grad()
, integrate()
, or the propensity_integrand function. method = simple
will vastly speed up the grad()
function.Here’s a few samples of interference()
based on the data provided.
The first example follows Perez-Heydrich 2014 and includes a random effect and participation variable. Conditional on participation, subjects were randomized to treatment with probability 2/3, which is the randomization
argument. This is an argument in logit_integrand()
. This argument defaults to \(1\) and so can be left out if unnecessary (see later examples).
sample1 <- interference(
allocations = c(.3, .45, .6), # a minimum of 2 is required
formula = y | A | B ~ X1 + X2 + (1|group) | group,
data = vaccinesim, # name of the data frame
randomization = 2/3,
method = 'simple' # speeds up grad()
)
## [1] "Calculating matrix of IP weights..."
## [1] "Calculating array of IP weight derivatives..."
## [1] "Calculating matrix of scores..."
## [1] "Computing effect estimates..."
## [1] "Interference complete"
Take a quick look using the (unpolished) print
function:
print(sample1)
## --------------------------------------------------------------------------
## Model Summary
## --------------------------------------------------------------------------
## Formula: y | A | B ~ X1 + X2 + (1 | group) | group
## Number of groups: 250
## 3 allocations were used from 0.3 (min) to 0.6 (max)
## --------------------------------------------------------------------------
## Causal Effect Summary
## Confidence level: 0.95
## Variance method: robust
## --------------------------------------------------------------------------
##
## Direct Effects
## alpha1 trt1 alpha2 trt2 estimate std.error conf.low conf.high
## 0.30 0 0.30 1 0.1605 0.02474 0.11201 0.2090
## 0.60 0 0.60 1 0.1086 0.01856 0.07220 0.1450
## 0.45 0 0.45 1 0.1339 0.01778 0.09904 0.1687
##
## Indirect Effects
## alpha1 trt1 alpha2 trt2 estimate std.error conf.low conf.high
## 0.30 0 0.60 0 0.15906 0.02617 0.10776 0.2104
## 0.30 0 0.45 0 0.08656 0.01732 0.05262 0.1205
## 0.45 0 0.60 0 0.07250 0.01408 0.04490 0.1001
##
## Total Effects
## alpha1 trt1 alpha2 trt2 estimate std.error conf.low conf.high
## 0.30 0 0.60 1 0.2676 0.02435 0.2199 0.3154
## 0.30 0 0.45 1 0.2205 0.02469 0.1721 0.2688
## 0.45 0 0.60 1 0.1811 0.01840 0.1450 0.2172
##
## Overall Effects
## alpha1 trt1 alpha2 trt2 estimate std.error conf.low conf.high
## 0.30 NA 0.60 NA 0.17606 0.01925 0.13834 0.2138
## 0.30 NA 0.45 NA 0.09867 0.01421 0.07082 0.1265
## 0.45 NA 0.60 NA 0.07740 0.00898 0.05980 0.0950
##
## --------------------------------------------------------------------------
Other pieces that might be interest are the group-level weights: \[ \frac{\prod_{j =1}^{n_i} \alpha^{A_{iij}}(1 - \alpha)^{1 - A_{ij}}}{P(\mathbf{A}_i | \mathbf{X}_i)} \] which can accessed:
# the matrix of weights
head(sample1$weights)
## 0.3 0.45 0.6
## 1 0.9358 1.3137 0.59574
## 2 0.2018 1.3140 2.75395
## 3 1.0451 1.8673 1.16436
## 4 2.7232 1.4569 0.18484
## 5 1.6131 0.5328 0.03575
## 6 1.1980 1.6818 0.76269
The weight ‘derivatives’: \[ \frac{\prod_{j =1}^{n_i} \alpha^{A_{iij}}(1 - \alpha)^{1 - A_{ij}}}{\frac{d}{d\theta}P(\mathbf{A}_i | \mathbf{X}_i)} \] which can accessed:
head(sample1$weightd[ , , 1]) # For the 1st allocation
## (Intercept) X1 X2 group.(Intercept)
## 1 -0.03692 1.121 -0.0686 0.40768
## 2 -0.14939 -0.417 -0.1434 -0.04413
## 3 -0.39947 -2.625 -0.2049 0.29168
## 4 0.39974 -8.601 0.4936 1.42415
## 5 0.69641 6.632 0.8187 0.60616
## 6 -0.12945 -1.829 -0.1168 0.49903
The ‘scores’ are but the all the last element in \(\psi(\mathbf{O}, \boldsymbol{\theta})\), eqn (3) in the web appendix, which can accessed:
head(sample1$scores)
## (Intercept) X1 X2 group.(Intercept)
## 1 0.5272 -2.99287 0.8440 -0.2719
## 2 0.6102 4.19001 0.5489 -0.1595
## 3 0.2427 -0.08583 0.1738 -0.5772
## 4 0.4655 3.74430 0.3534 -0.4215
## 5 -0.1741 -7.90318 -0.2339 -0.6825
## 6 -0.5450 0.88822 -0.9972 -0.3152
Finally, the most important piece, the effect estimates are in a data.frame:
sample1$estimates
## alpha1 trt1 alpha2 trt2 marginal effect_type effect estimate
## 1 0.30 0 NA NA FALSE outcome outcome 0.354295
## 2 0.45 0 NA NA FALSE outcome outcome 0.267731
## 3 0.60 0 NA NA FALSE outcome outcome 0.195234
## 4 0.30 1 NA NA FALSE outcome outcome 0.193796
## 5 0.45 1 NA NA FALSE outcome outcome 0.133838
## 6 0.60 1 NA NA FALSE outcome outcome 0.086646
## 7 0.30 NA NA NA TRUE outcome outcome 0.306146
## 8 0.45 NA NA NA TRUE outcome outcome 0.207479
## 9 0.60 NA NA NA TRUE outcome outcome 0.130081
## 10 0.30 1 0.30 0 FALSE contrast direct -0.160499
## 11 0.45 1 0.45 0 FALSE contrast direct -0.133893
## 12 0.60 1 0.60 0 FALSE contrast direct -0.108588
## 13 0.30 0 0.30 1 FALSE contrast direct 0.160499
## 14 0.45 0 0.45 1 FALSE contrast direct 0.133893
## 15 0.60 0 0.60 1 FALSE contrast direct 0.108588
## 16 0.30 0 0.30 0 FALSE contrast indirect 0.000000
## 17 0.45 0 0.30 0 FALSE contrast indirect -0.086565
## 18 0.60 0 0.30 0 FALSE contrast indirect -0.159061
## 19 0.30 1 0.30 1 FALSE contrast indirect 0.000000
## 20 0.45 1 0.30 1 FALSE contrast indirect -0.059958
## 21 0.60 1 0.30 1 FALSE contrast indirect -0.107150
## 22 0.30 0 0.45 0 FALSE contrast indirect 0.086565
## 23 0.45 0 0.45 0 FALSE contrast indirect 0.000000
## 24 0.60 0 0.45 0 FALSE contrast indirect -0.072497
## 25 0.30 1 0.45 1 FALSE contrast indirect 0.059958
## 26 0.45 1 0.45 1 FALSE contrast indirect 0.000000
## 27 0.60 1 0.45 1 FALSE contrast indirect -0.047192
## 28 0.30 0 0.60 0 FALSE contrast indirect 0.159061
## 29 0.45 0 0.60 0 FALSE contrast indirect 0.072497
## 30 0.60 0 0.60 0 FALSE contrast indirect 0.000000
## 31 0.30 1 0.60 1 FALSE contrast indirect 0.107150
## 32 0.45 1 0.60 1 FALSE contrast indirect 0.047192
## 33 0.60 1 0.60 1 FALSE contrast indirect 0.000000
## 34 0.30 1 0.30 0 FALSE contrast total -0.160499
## 35 0.45 1 0.30 0 FALSE contrast total -0.220457
## 36 0.60 1 0.30 0 FALSE contrast total -0.267649
## 37 0.30 1 0.45 0 FALSE contrast total -0.073934
## 38 0.45 1 0.45 0 FALSE contrast total -0.133893
## 39 0.60 1 0.45 0 FALSE contrast total -0.181085
## 40 0.30 1 0.60 0 FALSE contrast total -0.001438
## 41 0.45 1 0.60 0 FALSE contrast total -0.061396
## 42 0.60 1 0.60 0 FALSE contrast total -0.108588
## 43 0.30 0 0.30 1 FALSE contrast total 0.160499
## 44 0.45 0 0.30 1 FALSE contrast total 0.073934
## 45 0.60 0 0.30 1 FALSE contrast total 0.001438
## 46 0.30 0 0.45 1 FALSE contrast total 0.220457
## 47 0.45 0 0.45 1 FALSE contrast total 0.133893
## 48 0.60 0 0.45 1 FALSE contrast total 0.061396
## 49 0.30 0 0.60 1 FALSE contrast total 0.267649
## 50 0.45 0 0.60 1 FALSE contrast total 0.181085
## 51 0.60 0 0.60 1 FALSE contrast total 0.108588
## 52 0.30 NA 0.30 NA TRUE contrast overall 0.000000
## 53 0.45 NA 0.30 NA TRUE contrast overall -0.098667
## 54 0.60 NA 0.30 NA TRUE contrast overall -0.176064
## 55 0.30 NA 0.45 NA TRUE contrast overall 0.098667
## 56 0.45 NA 0.45 NA TRUE contrast overall 0.000000
## 57 0.60 NA 0.45 NA TRUE contrast overall -0.077398
## 58 0.30 NA 0.60 NA TRUE contrast overall 0.176064
## 59 0.45 NA 0.60 NA TRUE contrast overall 0.077398
## 60 0.60 NA 0.60 NA TRUE contrast overall 0.000000
## std.error conf.low conf.high
## 1 0.020854 0.31342 0.39517
## 2 0.014876 0.23857 0.29689
## 3 0.016208 0.16347 0.22700
## 4 0.018359 0.15781 0.22978
## 5 0.011494 0.11131 0.15637
## 6 0.009470 0.06809 0.10521
## 7 0.016644 0.27352 0.33877
## 8 0.010144 0.18760 0.22736
## 9 0.008728 0.11298 0.14719
## 10 0.024738 -0.20899 -0.11201
## 11 0.017782 -0.16874 -0.09904
## 12 0.018564 -0.14497 -0.07220
## 13 0.024738 0.11201 0.20899
## 14 0.017782 0.09904 0.16874
## 15 0.018564 0.07220 0.14497
## 16 0.000000 0.00000 0.00000
## 17 0.017318 -0.12051 -0.05262
## 18 0.026173 -0.21036 -0.10776
## 19 0.000000 0.00000 0.00000
## 20 0.013459 -0.08634 -0.03358
## 21 0.018918 -0.14423 -0.07007
## 22 0.017318 0.05262 0.12051
## 23 0.000000 0.00000 0.00000
## 24 0.014079 -0.10009 -0.04490
## 25 0.013459 0.03358 0.08634
## 26 0.000000 0.00000 0.00000
## 27 0.008271 -0.06340 -0.03098
## 28 0.026173 0.10776 0.21036
## 29 0.014079 0.04490 0.10009
## 30 0.000000 0.00000 0.00000
## 31 0.018918 0.07007 0.14423
## 32 0.008271 0.03098 0.06340
## 33 0.000000 0.00000 0.00000
## 34 0.024738 -0.20899 -0.11201
## 35 0.024688 -0.26884 -0.17207
## 36 0.024354 -0.31538 -0.21992
## 37 0.021565 -0.11620 -0.03167
## 38 0.017782 -0.16874 -0.09904
## 39 0.018402 -0.21715 -0.14502
## 40 0.025226 -0.05088 0.04800
## 41 0.019405 -0.09943 -0.02336
## 42 0.018564 -0.14497 -0.07220
## 43 0.024738 0.11201 0.20899
## 44 0.021565 0.03167 0.11620
## 45 0.025226 -0.04800 0.05088
## 46 0.024688 0.17207 0.26884
## 47 0.017782 0.09904 0.16874
## 48 0.019405 0.02336 0.09943
## 49 0.024354 0.21992 0.31538
## 50 0.018402 0.14502 0.21715
## 51 0.018564 0.07220 0.14497
## 52 0.000000 0.00000 0.00000
## 53 0.014208 -0.12651 -0.07082
## 54 0.019247 -0.21379 -0.13834
## 55 0.014208 0.07082 0.12651
## 56 0.000000 0.00000 0.00000
## 57 0.008980 -0.09500 -0.05980
## 58 0.019247 0.13834 0.21379
## 59 0.008980 0.05980 0.09500
## 60 0.000000 0.00000 0.00000
Helper functions for finding effects:
direct_effect(sample1, .3) #DE(.3)/ unfortunately de() is a function in utils.
## alpha1 trt1 alpha2 trt2 marginal effect_type effect estimate std.error
## 1 0.3 0 0.3 1 FALSE contrast direct 0.1605 0.02474
## conf.low conf.high
## 1 0.112 0.209
ie(sample1, .3, .6) #IE(.3, .6)
## alpha1 trt1 alpha2 trt2 marginal effect_type effect estimate std.error
## 1 0.3 0 0.6 0 FALSE contrast indirect 0.1591 0.02617
## conf.low conf.high
## 1 0.1078 0.2104
indirect_effect(sample1, .3, .6) # same
## alpha1 trt1 alpha2 trt2 marginal effect_type effect estimate std.error
## 1 0.3 0 0.6 0 FALSE contrast indirect 0.1591 0.02617
## conf.low conf.high
## 1 0.1078 0.2104
te(sample1, .3, .6) #TE(.3, .6)
## alpha1 trt1 alpha2 trt2 marginal effect_type effect estimate std.error
## 1 0.3 0 0.6 1 FALSE contrast total 0.2676 0.02435
## conf.low conf.high
## 1 0.2199 0.3154
oe(sample1, .3, .6) #OE(.3, .6)
## alpha1 trt1 alpha2 trt2 marginal effect_type effect estimate std.error
## 1 0.3 NA 0.6 NA TRUE contrast overall 0.1761 0.01925
## conf.low conf.high
## 1 0.1383 0.2138
# You can use the same functions to get all the effects. This will aid in
# plotting (see below.)
# All direct effect of constrast Y(0) - Y(1)
direct_effect(sample1)
## alpha1 trt1 alpha2 trt2 marginal effect_type effect estimate std.error
## 1 0.30 0 0.30 1 FALSE contrast direct 0.1605 0.02474
## 2 0.45 0 0.45 1 FALSE contrast direct 0.1339 0.01778
## 3 0.60 0 0.60 1 FALSE contrast direct 0.1086 0.01856
## conf.low conf.high
## 1 0.11201 0.2090
## 2 0.09904 0.1687
## 3 0.07220 0.1450
# to get Y(1) - Y(0) use trt.lvl1 argument
direct_effect(sample1, trt.lvl1 = 1)
## alpha1 trt1 alpha2 trt2 marginal effect_type effect estimate std.error
## 1 0.30 1 0.30 0 FALSE contrast direct -0.1605 0.02474
## 2 0.45 1 0.45 0 FALSE contrast direct -0.1339 0.01778
## 3 0.60 1 0.60 0 FALSE contrast direct -0.1086 0.01856
## conf.low conf.high
## 1 -0.2090 -0.11201
## 2 -0.1687 -0.09904
## 3 -0.1450 -0.07220
# Other functions work similarly
# all indirect effects where treatment = 0 compare to an allocation of .3
ie(sample1, .3)
## alpha1 trt1 alpha2 trt2 marginal effect_type effect estimate std.error
## 1 0.3 0 0.30 0 FALSE contrast indirect 0.00000 0.00000
## 2 0.3 0 0.45 0 FALSE contrast indirect 0.08656 0.01732
## 3 0.3 0 0.60 0 FALSE contrast indirect 0.15906 0.02617
## conf.low conf.high
## 1 0.00000 0.0000
## 2 0.05262 0.1205
## 3 0.10776 0.2104
See ?direct_effect
, ?ie
, ?te
, or ?oe
for options.
sample2 <- interference(
allocations = c(.3, .6), # a minimum of 2 is required
formula = y | A | B ~ X1 + X2 | group,
data = vaccinesim, # name of the data frame
model_method = 'glm',
model_options = list(family = binomial),
randomization = 2/3,
method = 'simple' # speeds up grad()
)
## [1] "Calculating matrix of IP weights..."
## [1] "Calculating array of IP weight derivatives..."
## [1] "Calculating matrix of scores..."
## [1] "Computing effect estimates..."
## [1] "Interference complete"
print(sample2)
## --------------------------------------------------------------------------
## Model Summary
## --------------------------------------------------------------------------
## Formula: y | A | B ~ X1 + X2 | group
## Number of groups: 250
## 2 allocations were used from 0.3 (min) to 0.6 (max)
## --------------------------------------------------------------------------
## Causal Effect Summary
## Confidence level: 0.95
## Variance method: robust
## --------------------------------------------------------------------------
##
## Direct Effects
## alpha1 trt1 alpha2 trt2 estimate std.error conf.low conf.high
## 0.3 0 0.3 1 0.3801 0.07570 0.23177 0.5285
## 0.6 0 0.6 1 0.1161 0.04215 0.03353 0.1987
##
## Indirect Effects
## alpha1 trt1 alpha2 trt2 estimate std.error conf.low conf.high
## 0.3 0 0.6 0 0.2953 0.08351 0.1316 0.4589
##
## Total Effects
## alpha1 trt1 alpha2 trt2 estimate std.error conf.low conf.high
## 0.3 0 0.6 1 0.4114 0.07698 0.2605 0.5623
##
## Overall Effects
## alpha1 trt1 alpha2 trt2 estimate std.error conf.low conf.high
## 0.3 NA 0.6 NA 0.2509 0.05691 0.1394 0.3624
##
## --------------------------------------------------------------------------
sample3 <- interference(
allocations = c(.3, .6), # a minimum of 2 is required
formula = y | A | B ~ X1 + X2 | group,
data = vaccinesim, # name of the data frame
model_method = 'oracle',
model_options = list(fixed.effects = c(0.2727, -0.0387, .2719),
random.effects = NULL),
causal_estimation_options = list(variance_estimation = 'naive'),
randomization = 2/3,
method = 'simple' # speeds up grad()
)
## [1] "Calculating matrix of IP weights..."
## [1] "Computing effect estimates..."
## [1] "Interference complete"
print(sample3)
## --------------------------------------------------------------------------
## Model Summary
## --------------------------------------------------------------------------
## Formula: y | A | B ~ X1 + X2 | group
## Number of groups: 250
## 2 allocations were used from 0.3 (min) to 0.6 (max)
## --------------------------------------------------------------------------
## Causal Effect Summary
## Confidence level: 0.95
## Variance method: naive
## --------------------------------------------------------------------------
##
## Direct Effects
## alpha1 trt1 alpha2 trt2 estimate std.error conf.low conf.high
## 0.3 0 0.3 1 0.51883 0.09880 0.32519 0.7125
## 0.6 0 0.6 1 0.09991 0.02622 0.04851 0.1513
##
## Indirect Effects
## alpha1 trt1 alpha2 trt2 estimate std.error conf.low conf.high
## 0.3 0 0.6 0 0.5162 0.1071 0.3064 0.7261
##
## Total Effects
## alpha1 trt1 alpha2 trt2 estimate std.error conf.low conf.high
## 0.3 0 0.6 1 0.6161 0.1042 0.4119 0.8204
##
## Overall Effects
## alpha1 trt1 alpha2 trt2 estimate std.error conf.low conf.high
## 0.3 NA 0.6 NA 0.4205 0.07675 0.2701 0.5709
##
## --------------------------------------------------------------------------
Suppose we don’t have the participation variable and estimate the treatment probability directly, just leave out the randomization
argument and modify the formula:
sample4 <- interference(
allocations = c(.3, .6), # a minimum of 2 is required
formula = y | A ~ X1 + X2 | group,
data = vaccinesim, # name of the data frame
model_method = 'glm',
causal_estimation_options = list(variance_estimation = 'robust'),
method = 'simple' # speeds up grad()
)
## [1] "Calculating matrix of IP weights..."
## [1] "Calculating array of IP weight derivatives..."
## [1] "Calculating matrix of scores..."
## [1] "Computing effect estimates..."
## [1] "Interference complete"
print(sample4)
## --------------------------------------------------------------------------
## Model Summary
## --------------------------------------------------------------------------
## Formula: y | A ~ X1 + X2 | group
## Number of groups: 250
## 2 allocations were used from 0.3 (min) to 0.6 (max)
## --------------------------------------------------------------------------
## Causal Effect Summary
## Confidence level: 0.95
## Variance method: robust
## --------------------------------------------------------------------------
##
## Direct Effects
## alpha1 trt1 alpha2 trt2 estimate std.error conf.low conf.high
## 0.3 0 0.3 1 0.3622 0.06846 0.22805 0.4964
## 0.6 0 0.6 1 0.1158 0.03900 0.03938 0.1923
##
## Indirect Effects
## alpha1 trt1 alpha2 trt2 estimate std.error conf.low conf.high
## 0.3 0 0.6 0 0.272 0.07107 0.1327 0.4113
##
## Total Effects
## alpha1 trt1 alpha2 trt2 estimate std.error conf.low conf.high
## 0.3 0 0.6 1 0.3878 0.06584 0.2588 0.5169
##
## Overall Effects
## alpha1 trt1 alpha2 trt2 estimate std.error conf.low conf.high
## 0.3 NA 0.6 NA 0.2328 0.04754 0.1397 0.326
##
## --------------------------------------------------------------------------
Let’s say you want to fix the group level propensity to be .5. I don’t know why you’d want to do this, but this illustrates how to write your own function. The function required three arguments: b
, x
, and pos
. b
must be the first argument. x
and pos
are necessary for the grad()
, and I will describe how to use these later.
myFUN <- function(b, x, pos){
return(.5 * dnorm(b))
}
integrate(myFUN, l = -Inf, u = Inf) # returns 0.5
## 0.5 with absolute error < 4.7e-05
sample5 <- interference(
propensity_integrand = 'myFUN',
allocations = c(.3, .6), # a minimum of 2 is required
formula = y | A ~ X1 + X2 | group,
data = vaccinesim, # name of the data frame
model_method = 'glm',
causal_estimation_options = list(variance_estimation = 'naive'),
# won't work for 'robust' unless addition arguments are defined
method = 'simple' # speeds up grad()
)
## [1] "Calculating matrix of IP weights..."
## [1] "Computing effect estimates..."
## [1] "Interference complete"
print(sample5)
## --------------------------------------------------------------------------
## Model Summary
## --------------------------------------------------------------------------
## Formula: y | A ~ X1 + X2 | group
## Number of groups: 250
## 2 allocations were used from 0.3 (min) to 0.6 (max)
## --------------------------------------------------------------------------
## Causal Effect Summary
## Confidence level: 0.95
## Variance method: naive
## --------------------------------------------------------------------------
##
## Direct Effects
## alpha1 trt1 alpha2 trt2 estimate std.error conf.low conf.high
## 0.3 0 0.3 1 0.004928 0.0018947 0.0012149 0.008642
## 0.6 0 0.6 1 0.001124 0.0004795 0.0001841 0.002064
##
## Indirect Effects
## alpha1 trt1 alpha2 trt2 estimate std.error conf.low conf.high
## 0.3 0 0.6 0 0.004436 0.00151 0.001477 0.007394
##
## Total Effects
## alpha1 trt1 alpha2 trt2 estimate std.error conf.low conf.high
## 0.3 0 0.6 1 0.00556 0.001883 0.00187 0.00925
##
## Overall Effects
## alpha1 trt1 alpha2 trt2 estimate std.error conf.low conf.high
## 0.3 NA 0.6 NA 0.003632 0.001166 0.001346 0.005917
##
## --------------------------------------------------------------------------
Here’s a simple plot of direct effects. Run the interference
function with a larger number of allocations (this will take longer!):
sample6 <- interference(
allocations = seq(.3, .6, by = .01),
formula = y | A ~ X1 + X2 | group,
data = vaccinesim, # name of the data frame
model_method = 'glm',
causal_estimation_options = list(variance_estimation = 'robust'),
method = 'simple' # speeds up grad()
)
## [1] "Calculating matrix of IP weights..."
## [1] "Calculating array of IP weight derivatives..."
## [1] "Calculating matrix of scores..."
## [1] "Computing effect estimates..."
## [1] "Interference complete"
# Look at the direct effects
deff <- direct_effect(sample6)
# Plot the point estimates
plot(deff$alpha1, deff$estimate, type = 'l')