R/eggers.test.R

Defines functions eggers.test

Documented in eggers.test

#' Perform Egger's test of the intercept
#'
#' This function performs Egger's test of the intercept for funnel plot asymmetry using an object
#' of class \code{meta}.
#'
#' @usage eggers.test(x)
#'
#' @param x An object of class \code{meta}, generated by the \code{metabin}, \code{metagen},
#' \code{metacont}, \code{metacor}, \code{metainc}, or \code{metaprop} function.
#'
#' @details Performs Egger's test (Egger et al., 1997) for funnel plot asymmetry.
#' The \code{\link[meta]{metabias}} function is called internally. Egger's test may lack
#' the statistical power to detect bias when the number of studies is small. Sterne et al.
#' (2011) recommend to perform funnel plot asymmetry tests only when \eqn{k \geq 10}. A warning
#' is therefore printed when the number of studies in the \code{meta} object is \eqn{k < 10}.
#'
#' @references
#'
#' Harrer, M., Cuijpers, P., Furukawa, T.A, & Ebert, D. D. (2019).
#' \emph{Doing Meta-Analysis in R: A Hands-on Guide}. DOI: 10.5281/zenodo.2551803. \href{https://bookdown.org/MathiasHarrer/Doing_Meta_Analysis_in_R/smallstudyeffects.html}{Chapter 9.1}
#'
#' Egger M, Smith GD, Schneider M & Minder C (1997), Bias in meta-analysis detected by a simple,
#' graphical test. \emph{BMJ}, 315, 629–634.
#'
#' Sterne, JAC et al. (2011), Recommendations for Examining and Interpreting Funnel Plot
#' Asymmetry in Meta-Analyses of Randomised Controlled Trials. \emph{BMJ}
#' 343, 1, doi: 10.1136/bmj.d4002 .
#'
#' @author Mathias Harrer & David Daniel Ebert
#'
#' @importFrom meta metabias
#' @importFrom graphics abline axis lines mtext par plot points rect segments text
#' @importFrom stats as.formula hat influence ks.test optimize pbinom pchisq pf pnorm pt punif qchisq qf qnorm qt reformulate reorder setNames uniroot
#'
#' @return Returns a list containing the following elements:
#' \itemize{
#' \item \code{intercept}: The intercept (bias).
#' \item \code{llci}: The lower bound of the 95\% intercept confidence interval.
#' \item \code{ulci}: The upper bound of the 95\% intercept confidence interval.
#' \item \code{t}: The t-statistic for the intercept test.
#' \item \code{p}: The \eqn{p}-value for Egger's test.
#' \item \code{meta.obj}: The meta-analysis object of class \code{meta} originally provided
#' to the function.
#' }
#'
#' @export eggers.test
#'
#' @seealso \code{\link[meta]{metabias}}
#'
#' @examples
#' # Create meta-analysis results using the 'metagen' function
#' suppressPackageStartupMessages(library(meta))
#' data(ThirdWave)
#' m = metagen(TE, seTE, studlab = paste(Author),
#'     data = ThirdWave, random = TRUE, hakn=TRUE)
#'
#' # Plug result into 'eggers.test' function
#' res.et <- eggers.test(m)
#'
#' # Inspect the results
#' summary(res.et)
#'
#' # Generate a funnel plot. This calls the 'funnel' function
#' # in 'meta' internally; additional parameters of this function can also
#' # be provided (see '?meta::funnel').
#' plot(res.et, bg = "lightblue")


eggers.test = function(x) {

    # Validate
    x = x

    if (x$k < 10) {

        warning(paste("Your meta-analysis contains k =",
                      x$k, "studies. Egger's test may lack the statistical power to detect bias when the number of studies is small (i.e., k<10)."))

    }

    if (class(x)[1] %in% c("meta", "metabin", "metagen", "metacont", "metacor", "metainc", "metaprop")) {

        # Conduct metabias
        eggers = meta::metabias(x, k.min = 3, method = "linreg")

        # Get Intercept
        intercept = as.numeric(eggers$estimate[1])

        # Get SE
        se = as.numeric(eggers$estimate[2])

        # Calculate 95CI
        llci = intercept - qnorm(0.975) * se
        ulci = intercept + qnorm(0.975) * se

        # Get t
        t = as.numeric(eggers$statistic)

        # Get df
        df = as.numeric(eggers$parameters)

        # Get p
        p = as.numeric(eggers$p.value)

        # Make df
        returnlist = list(intercept = intercept,
                          llci = llci,
                          ulci = ulci,
                          t = t,
                          p = p,
                          meta.obj = x)

    } else {

        stop("x must be of type 'metabin', 'metagen', 'metacont', 'metainc' or 'metaprop'")

    }

    class(returnlist) = "eggers.test"

    return(returnlist)

}
MathiasHarrer/dmetar documentation built on April 4, 2024, 6:57 p.m.