Skip to contents

This vignette shows examples of all currently supported varcov_type metric options for within-study variance-covariance computation in mars.

library(mars)

1. Correlation Metrics

For synthesized correlation matrices, use:

  • simple
  • weighted
  • average
cor_dat <- data.frame(
  study = c("s1", "s1", "s1", "s2", "s2", "s2"),
  numID = c(1, 2, 3, 1, 2, 3),
  ri = c(0.20, 0.12, 0.08, 0.25, 0.15, 0.11),
  N = c(100, 100, 100, 120, 120, 120)
)

S_cor_simple <- mars:::within_varcov(
  data = cor_dat,
  N = "N",
  effect_name = "ri",
  study = "study",
  type = "simple"
)

S_cor_weighted <- mars:::within_varcov(
  data = cor_dat,
  N = "N",
  effect_name = "ri",
  study = "study",
  type = "weighted"
)

S_cor_average <- mars:::within_varcov(
  data = cor_dat,
  N = "N",
  effect_name = "ri",
  study = "study",
  type = "average"
)

S_cor_simple[[1]]
#>             [,1]        [,2]        [,3]
#> [1,] 0.009216000 0.000643776 0.001069184
#> [2,] 0.000643776 0.009714074 0.001913318
#> [3,] 0.001069184 0.001913318 0.009872410
S_cor_weighted[[1]]
#>              [,1]         [,2]        [,3]
#> [1,] 0.0089936224 0.0007533087 0.001179743
#> [2,] 0.0007533087 0.0096315569 0.002148884
#> [3,] 0.0011797431 0.0021488845 0.009815143
S_cor_average[[1]]
#>              [,1]         [,2]        [,3]
#> [1,] 0.0090131289 0.0007445448 0.001170920
#> [2,] 0.0007445448 0.0096388215 0.002129556
#> [3,] 0.0011709204 0.0021295562 0.009820315

2. SMD by Outcome (existing)

For multiple SMD outcomes within study, use:

  • outcome
smd_outcome_dat <- data.frame(
  study = c("s1", "s1", "s2", "s2"),
  d = c(0.30, 0.42, 0.20, 0.27),
  nt = c(40, 40, 36, 36),
  nc = c(40, 40, 36, 36),
  r2do = c(0.7, 0.7, 0.7, 0.7)
)

S_smd_outcome <- mars:::within_varcov(
  data = smd_outcome_dat,
  N = NULL,
  effect_name = "d",
  study = "study",
  type = "outcome"
)

S_smd_outcome[[1]]
#>            [,1]       [,2]
#> [1,] 0.05056250 0.03538587
#> [2,] 0.03538587 0.05110250

3. SMD with Shared Control Group

For multiple treatment arms sharing one control within study, use:

  • smd_shared_control (aliases: smd_control, control)
smd_shared_dat <- data.frame(
  study = c("s1", "s1", "s2", "s2"),
  effID = c(1, 2, 1, 2),
  yi = c(0.22, 0.35, 0.18, 0.28),
  nt = c(50, 55, 48, 46),
  nc = c(60, 60, 52, 52),
  control_id = c("c1", "c1", "c2", "c2")
)

S_smd_control <- mars:::within_varcov(
  data = smd_shared_dat,
  N = NULL,
  effect_name = "yi",
  study = "study",
  type = "smd_shared_control"
)

S_smd_control[[1]]
#>            [,1]       [,2]
#> [1,] 0.03688667 0.01730833
#> [2,] 0.01730833 0.03538109

4. Log Relative Risk (shared control)

Use:

  • log_rr (aliases: rr, relative_risk, risk_ratio)

Required columns are treatment/control events and totals (for example, tpos, tneg, cpos, cneg), or equivalent aliases.

rr_dat <- data.frame(
  study = c("s1", "s1", "s2", "s2"),
  effID = c(1, 2, 1, 2),
  tpos = c(20, 18, 16, 14),
  tneg = c(30, 37, 32, 30),
  cpos = c(15, 15, 14, 14),
  cneg = c(45, 45, 38, 38),
  control_id = c("c1", "c1", "c2", "c2")
)
nt <- rr_dat$tpos + rr_dat$tneg
nc <- rr_dat$cpos + rr_dat$cneg
rr_dat$yi <- log((rr_dat$tpos / nt) / (rr_dat$cpos / nc))

S_log_rr <- mars:::within_varcov(
  data = rr_dat,
  N = NULL,
  effect_name = "yi",
  study = "study",
  type = "log_rr"
)

S_log_rr[[1]]
#>      [,1]       [,2]
#> [1,] 0.08 0.05000000
#> [2,] 0.05 0.08737374

5. Log Odds Ratio (shared control)

Use:

  • log_or (aliases: or, log_odds_ratio)
or_dat <- rr_dat
or_dat$yi <- log((or_dat$tpos / or_dat$tneg) / (or_dat$cpos / or_dat$cneg))

S_log_or <- mars:::within_varcov(
  data = or_dat,
  N = NULL,
  effect_name = "yi",
  study = "study",
  type = "log_or"
)

S_log_or[[1]]
#>            [,1]       [,2]
#> [1,] 0.17222222 0.08888889
#> [2,] 0.08888889 0.17147147

6. Single-arm Proportions

Use:

  • proportion (alias: prop)

Required columns: events and totals (for example, events, n).

prop_dat <- data.frame(
  study = c("s1", "s1", "s2", "s2"),
  effID = c(1, 2, 1, 2),
  events = c(14, 18, 10, 13),
  n = c(60, 62, 55, 57)
)
prop_dat$yi <- prop_dat$events / prop_dat$n

S_prop <- mars:::within_varcov(
  data = prop_dat,
  N = NULL,
  effect_name = "yi",
  study = "study",
  type = "proportion"
)

S_prop[[1]]
#>             [,1]        [,2]
#> [1,] 0.002981481 0.000000000
#> [2,] 0.000000000 0.003323151

7. Proportion Differences / Risk Difference (shared control)

Use:

  • proportion_diff (aliases: prop_diff, risk_difference)
pd_dat <- rr_dat
nt <- pd_dat$tpos + pd_dat$tneg
nc <- pd_dat$cpos + pd_dat$cneg
pd_dat$yi <- (pd_dat$tpos / nt) - (pd_dat$cpos / nc)

S_prop_diff <- mars:::within_varcov(
  data = pd_dat,
  N = NULL,
  effect_name = "yi",
  study = "study",
  type = "proportion_diff"
)

S_prop_diff[[1]]
#>          [,1]        [,2]
#> [1,] 0.007925 0.003125000
#> [2,] 0.003125 0.007128005

8. Continuous Outcomes with Shared Controls

For raw mean differences and log response ratios with multiple treatment arms sharing one control, use:

  • mean_diff (aliases: raw_mean_diff, md)
  • log_response_ratio (aliases: response_ratio, rom, lnrr_continuous)

These structures use treatment/control sample sizes and standard deviations; log response ratios also use treatment/control means.

cont_dat <- data.frame(
  study = c("s1", "s1", "s2", "s2"),
  control_id = c("c1", "c1", "c2", "c2"),
  mt = c(5.8, 6.1, 5.2, 5.4),
  mc = c(4.6, 4.6, 4.4, 4.4),
  sdt = c(1.4, 1.5, 1.3, 1.2),
  sdc = c(1.2, 1.2, 1.1, 1.1),
  nt = c(45, 48, 42, 41),
  nc = c(50, 50, 44, 44)
)
cont_dat$yi <- cont_dat$mt - cont_dat$mc

S_md <- mars:::within_varcov(
  data = cont_dat,
  N = NULL,
  effect_name = "yi",
  study = "study",
  type = "mean_diff"
)

cont_dat$yi <- log(cont_dat$mt / cont_dat$mc)
S_rom <- mars:::within_varcov(
  data = cont_dat,
  N = NULL,
  effect_name = "yi",
  study = "study",
  type = "log_response_ratio"
)

S_md[[1]]
#>            [,1]     [,2]
#> [1,] 0.07235556 0.028800
#> [2,] 0.02880000 0.075675
S_rom[[1]]
#>             [,1]        [,2]
#> [1,] 0.002655814 0.001361059
#> [2,] 0.001361059 0.002620801

9. Standardized Mean Change / Repeated Measures

For pre-post standardized mean change effects, use:

  • standardized_mean_change (aliases: smc, pre_post_smd, repeated_measures_smd)

The diagonal uses sample size, the effect size, and the pre-post correlation. When an outcome-correlation column such as r2do or rho is supplied, rows with the same sample_id receive an approximate off-diagonal covariance.

smc_dat <- data.frame(
  study = c("s1", "s1", "s2", "s2"),
  sample_id = c("a", "a", "b", "b"),
  yi = c(0.35, 0.42, 0.22, 0.31),
  n = c(40, 40, 35, 35),
  r_pre_post = c(0.60, 0.60, 0.55, 0.55),
  r2do = c(0.50, 0.50, 0.45, 0.45)
)

S_smc <- mars:::within_varcov(
  data = smc_dat,
  N = NULL,
  effect_name = "yi",
  study = "study",
  type = "standardized_mean_change"
)

S_smc[[1]]
#>            [,1]       [,2]
#> [1,] 0.02153125 0.01093277
#> [2,] 0.01093277 0.02220500

10. Incidence Rates and Survival Summaries

For Poisson-style event rates with person-time denominators, use:

  • log_rate_ratio (aliases: rate_ratio, incidence_rate_ratio)
  • rate_difference (alias: incidence_rate_difference)

For log hazard ratios, use:

  • log_hr (aliases: hr, hazard_ratio)

The log-hazard-ratio path is diagonal and requires an explicit variance or standard-error column, because shared-arm survival covariances cannot generally be recovered from a published log HR alone.

rate_dat <- data.frame(
  study = c("s1", "s1", "s2", "s2"),
  control_id = c("c1", "c1", "c2", "c2"),
  event_t = c(18, 21, 12, 14),
  event_c = c(15, 15, 10, 10),
  person_time_t = c(120, 130, 100, 105),
  person_time_c = c(140, 140, 95, 95)
)
rate_dat$yi <- log((rate_dat$event_t / rate_dat$person_time_t) /
                     (rate_dat$event_c / rate_dat$person_time_c))

S_rate_ratio <- mars:::within_varcov(
  data = rate_dat,
  N = NULL,
  effect_name = "yi",
  study = "study",
  type = "log_rate_ratio"
)

hr_dat <- data.frame(
  study = c("s1", "s1", "s2"),
  yi = c(log(0.80), log(1.10), log(0.95)),
  sei = c(0.12, 0.15, 0.18)
)

S_hr <- mars:::within_varcov(
  data = hr_dat,
  N = NULL,
  effect_name = "yi",
  study = "study",
  type = "log_hr"
)

S_rate_ratio[[1]]
#>            [,1]       [,2]
#> [1,] 0.12222222 0.06666667
#> [2,] 0.06666667 0.11428571
S_hr[[1]]
#>        [,1]   [,2]
#> [1,] 0.0144 0.0000
#> [2,] 0.0000 0.0225

11. Transformed Proportions

For transformed single-arm proportions, use:

  • logit_proportion (alias: logit_prop)
  • arcsine_proportion (alias: arcsine_prop)
  • freeman_tukey_proportion (aliases: freeman_tukey_prop, pft)
S_logit_prop <- mars:::within_varcov(
  data = prop_dat,
  N = NULL,
  effect_name = "yi",
  study = "study",
  type = "logit_proportion"
)

S_arcsine_prop <- mars:::within_varcov(
  data = prop_dat,
  N = NULL,
  effect_name = "yi",
  study = "study",
  type = "arcsine_proportion"
)

S_ft_prop <- mars:::within_varcov(
  data = prop_dat,
  N = NULL,
  effect_name = "yi",
  study = "study",
  type = "freeman_tukey_proportion"
)

S_logit_prop[[1]]
#>           [,1]       [,2]
#> [1,] 0.0931677 0.00000000
#> [2,] 0.0000000 0.07828283
S_arcsine_prop[[1]]
#>             [,1]        [,2]
#> [1,] 0.004166667 0.000000000
#> [2,] 0.000000000 0.004032258
S_ft_prop[[1]]
#>             [,1]  [,2]
#> [1,] 0.004132231 0.000
#> [2,] 0.000000000 0.004

12. Partial Correlations, Fisher z, and Reliability

Correlation-matrix workflows can also use Fisher-z transformed correlations:

  • fisher_z_simple, fisher_z_weighted, fisher_z_average

The function converts z values back to correlations for the Olkin-Siotani calculation, then applies a delta-method transformation back to the z scale.

Partial correlations and reliability coefficients use diagonal approximations:

  • partial_cor (aliases: partial_correlation, partial_r)
  • partial_fisher_z (alias: partial_z)
  • reliability (aliases: cronbach_alpha, alpha)
  • log_reliability
pc_dat <- data.frame(
  study = c("s1", "s1", "s2"),
  yi = c(0.20, 0.30, 0.18),
  n = c(80, 82, 75),
  p = c(3, 3, 2)
)

S_partial <- mars:::within_varcov(
  data = pc_dat,
  N = NULL,
  effect_name = "yi",
  study = "study",
  type = "partial_cor"
)

rel_dat <- data.frame(
  study = c("s1", "s1", "s2"),
  alpha = c(0.82, 0.78, 0.85),
  n = c(100, 95, 110),
  items = c(8, 7, 9)
)

S_reliability <- mars:::within_varcov(
  data = rel_dat,
  N = NULL,
  effect_name = "alpha",
  study = "study",
  type = "reliability"
)

S_partial[[1]]
#>            [,1]       [,2]
#> [1,] 0.01245405 0.00000000
#> [2,] 0.00000000 0.01089605
S_reliability[[1]]
#>              [,1]        [,2]
#> [1,] 0.0007556851 0.000000000
#> [2,] 0.0000000000 0.001214337

13. Generic Diagonal Options

For purely diagonal within-study structures:

  • univariate (vector per study, for univariate analysis)
  • multilevel (diagonal matrix per study)
diag_dat <- data.frame(
  study = c("s1", "s1", "s2"),
  vi = c(0.04, 0.05, 0.03)
)

S_uni <- mars:::within_varcov(
  data = diag_dat,
  N = NULL,
  effect_name = "yi",
  study = "study",
  type = "univariate",
  variance = "vi"
)

S_ml <- mars:::within_varcov(
  data = diag_dat,
  N = NULL,
  effect_name = "yi",
  study = "study",
  type = "multilevel",
  variance = "vi"
)

S_uni[[1]]
#> [1] 0.04 0.05
S_ml[[1]]
#>      [,1] [,2]
#> [1,] 0.04 0.00
#> [2,] 0.00 0.05

These same varcov_type values can be passed to mars() / estimation() for multivariate analyses.

Method References

The covariance structures follow large-sample approximations for dependent effect sizes and common meta-analytic effect-size transformations. General dependent-effect-size formulas are anchored by Gleser and Olkin (2009) and Viechtbauer (2010). Correlation-matrix covariances use Olkin and Siotani (1976). Standardized mean differences and standardized mean change draw on Hedges and Olkin (1985), Becker (1988), and Morris (2008). Continuous response ratios draw on Lajeunesse (2011) and Friedrich, Adhikari, and Beyene (2011). Survival summaries draw on Parmar, Torri, and Stewart (1998) and Tierney et al. (2007). Transformed proportions draw on Freeman and Tukey (1950) and Barendregt et al. (2013). Reliability-coefficient approximations draw on Cronbach (1951) and Bonett (2002). Partial-correlation support is aligned with Aloe and Thompson (2013) and Aloe et al. (2016).