knitr::opts_chunk$set(echo = TRUE)
library(gt)
library(dplyr)
library(tidyr)
library(tibble)
library(ggplot2)
library(gsDesign)
devtools::load_all()

Overview

We consider a delayed effect scenario where

enrollRates <- tibble(Stratum = "All", duration = 12, rate = 1)
failRates <- tibble(Stratum = "All",
                            duration = c(6, 100),
                            failRate = log(2) / 15,
                            hr = c(1, .6),
                            dropoutRate = 0.001)
enrollRates %>% gt() %>% tab_header(title = "Enrollment Table of Scenario 1")
failRates %>% gt() %>% tab_header(title = "Failure Table of Scenario 1")

For the above scenarios, we investigate the power, sample size and events under 6 tests:

We then compute power for the logrank test. The general summary is that the Fleming-Harrington test has a meaningful power gain relative to logrank regardless of the study durations evaluated.

tab <- NULL

for(trial_duration in seq(24, 60, 4)){

  # Fleming-Harrington rho=0, gamma=0.5 test
  FH05 <- gs_design_wlr(enrollRates = enrollRates, 
                        failRates = failRates,
                        ratio = 1, 
                        alpha = 0.025, beta = 0.15,
                        weight = function(x, arm0, arm1){wlr_weight_fh(x, arm0, arm1, rho = 0, gamma = 0.5)},
                        upar = qnorm(.975),
                        lpar = -Inf,
                        analysisTimes = trial_duration) 

  # regular logrank test
  FH00 <- gs_power_wlr(enrollRates = FH05$enrollRates, 
                       failRates = failRates,
                       ratio = 1, 
                       weight = function(x, arm0, arm1){wlr_weight_fh(x, arm0, arm1, rho = 0, gamma = 0)},
                       upar = qnorm(.975),
                       lpar = -Inf,
                       analysisTimes = trial_duration,
                       events = .1) 

  # max combo test 1
  mc2_test <- data.frame(rho = 0, gamma = c(0, .5), tau = -1,
                         test = 1:2, Analysis = 1, analysisTimes = trial_duration)

  MC2 <- gs_power_combo(enrollRates = FH05$enrollRates, 
                        failRates = failRates, 
                        fh_test = mc2_test,
                        upper = gs_spending_combo,
                   upar  = list(sf = gsDesign::sfLDOF, total_spend = 0.025),
                   lower = gs_spending_combo,
                   lpar  = list(sf = gsDesign::sfLDOF, total_spend = 0.01))

  # max combo test 2
  mc3_test <- data.frame(rho = c(0, 0, .5), gamma = c(0, .5, .5), tau = -1,
                         test = 1:3, Analysis = 1, analysisTimes = trial_duration)

  MC3 <- gs_power_combo(enrollRates = FH05$enrollRates, 
                        failRates = failRates, 
                        fh_test = mc3_test,
                        upper = gs_spending_combo,
                        upar  = list(sf = gsDesign::sfLDOF, total_spend = 0.025),
                        lower = gs_spending_combo,
                        lpar  = list(sf = gsDesign::sfLDOF, total_spend = 0.01))

  # max combo test 
  mc4_test <- data.frame(rho = c(0, 0, .5, .5), gamma = c(0, .5, .5, 0), tau = -1,
                         test = 1:4, Analysis = 1, analysisTimes = trial_duration)

  MC4 <- gs_power_combo(enrollRates = FH05$enrollRates, 
                        failRates = failRates, 
                        fh_test = mc4_test,
                        upper = gs_spending_combo,
                        upar  = list(sf = gsDesign::sfLDOF, total_spend = 0.025),
                        lower = gs_spending_combo,
                        lpar  = list(sf = gsDesign::sfLDOF, total_spend = 0.01))

  # Magirr-Burman rho=-1, gamma=0, tau = 6 test
  MB6 <- gs_power_wlr(enrollRates = FH05$enrollRates, 
                      failRates = failRates,
                      ratio = 1, 
                      weight = function(x, arm0, arm1){wlr_weight_fh(x, arm0, arm1, rho = -1, gamma = 0, tau = 20)},
                      upar = qnorm(.975),
                      lpar = -Inf,
                      analysisTimes = trial_duration,
                      events = .1) 

  tab_new <- tibble(`Study duration` = trial_duration,
                    N = FH05$analysis$N[1],
                    Events = FH05$analysi$Events[1], 
                    `Events/N` = Events/N, 
                    # we use the AHR from regular WLR as the AHR of different max combo test
                    AHR = as.numeric(FH00$analysis$AHR[1]), 
                    `FH(0, 0.5) power` = FH05$bounds$Probability[1],
                    `FH(0, 0) power` = FH00$bounds$Probability[1],
                    `MC2 power` = MC2$bounds$Probability[1],
                    `MC4 power` = MC4$bounds$Probability[1],
                    `MC3 power` = MC3$bounds$Probability[1],
                    `MB6 power` = MB6$bounds$Probability[1])
  tab <- rbind(tab, tab_new)
}

tab %>% 
  gt() %>%
  fmt_number(columns = c(2, 3), decimals = 1) %>%
  fmt_number(columns = 4, decimals = 2) %>%
  fmt_number(columns = 5, decimals = 4) %>%
  fmt_number(columns = 6:11, decimals = 2)

An Alternative Scenario

Now we consider an alternate scenario where the placebo group starts with the same median, but then has a piecewise change to a median of 30 after 16 months and with a hazard ratio of 0.85 during that late period.

enrollRates <- tibble(Stratum = "All", duration = 12, rate = 1)
failRates <- tibble(Stratum = "All",
                    duration = c(6, 10, 100),
                    # in Scenario 1: failRate = log(2) / 15,
                    failRate = log(2) / c(15, 15, 30),
                    # in Scenario 1: hr = c(1, .6)
                    hr = c(1, .6, .85),
                    dropoutRate = 0.001)
enrollRates %>% gt() %>% tab_header(title = "Enrollment Table of Scenario 2")
failRates %>% gt() %>% tab_header(title = "Failure Table of Scenario 2")
tab <- NULL

for(trial_duration in seq(20, 60, 4)){
  # Fleming-Harrington rho=0, gamma=0.5 test
  FH05 <- gs_design_wlr(enrollRates = enrollRates, 
                        failRates = failRates,
                        ratio = 1,
                        alpha = 0.025, beta = 0.15,
                        weight = function(x, arm0, arm1){wlr_weight_fh(x, arm0, arm1, rho = 0, gamma = 0.5)},
                        upper = gs_b,
                        upar = qnorm(.975),
                        lower = gs_b,
                        lpar = -Inf,
                        analysisTimes = trial_duration) 

  # regular logrank test
  FH00 <- gs_power_wlr(enrollRates = FH05$enrollRates, 
                       failRates = failRates,
                       ratio = 1, 
                       weight = function(x, arm0, arm1){wlr_weight_fh(x, arm0, arm1, rho = 0, gamma = 0)},
                       upper = gs_b,
                       upar = qnorm(.975),
                       lower = gs_b,
                       lpar = -Inf,
                       analysisTimes = trial_duration,
                       events = .1)

  # max combo test 
  mc2_test <- data.frame(rho = 0, gamma = c(0, .5), tau = -1,
                         test = 1:2, Analysis = 1, analysisTimes = trial_duration)
  MC2 <- gs_power_combo(enrollRates = FH05$enrollRates, 
                        failRates = failRates, 
                        fh_test = mc2_test,
                        upper = gs_spending_combo,
                        upar  = list(sf = gsDesign::sfLDOF, total_spend = 0.025),
                        lower = gs_spending_combo,
                        lpar  = list(sf = gsDesign::sfLDOF, total_spend = 0.01))

  # max combo test 
  mc3_test <- data.frame(rho = c(0,0,.5), gamma = c(0, .5, .5), tau = -1,
                         test = 1:3, Analysis = 1, analysisTimes = trial_duration)

  MC3 <- gs_power_combo(enrollRates = FH05$enrollRates, 
                        failRates = failRates, 
                        fh_test = mc3_test,
                        upper = gs_spending_combo,
                        upar  = list(sf = gsDesign::sfLDOF, total_spend = 0.025),
                        lower = gs_spending_combo,
                        lpar  = list(sf = gsDesign::sfLDOF, total_spend = 0.01))

  # max combo test 
  mc4_test <- data.frame(rho = c(0,0,.5,.5), gamma = c(0, .5, .5, 0), tau = -1,
                         test = 1:4, Analysis = 1, analysisTimes = trial_duration)

  MC4 <- gs_power_combo(enrollRates = FH05$enrollRates, 
                        failRates = failRates, fh_test = mc4_test,
                        upper = gs_spending_combo,
                        upar  = list(sf = gsDesign::sfLDOF, total_spend = 0.025),
                        lower = gs_spending_combo,
                        lpar  = list(sf = gsDesign::sfLDOF, total_spend = 0.01))

  # Magirr-Burman rho=-1, gamma=0, tau = 6 test
  MB6 <- gs_power_wlr(enrollRates = FH05$enrollRates, 
                      failRates = failRates,
                      ratio = 1, 
                      weight = function(x, arm0, arm1){wlr_weight_fh(x, arm0, arm1, rho = -1, gamma = 0, tau = 6)},
                      upar = qnorm(.975),
                      lpar = -Inf,
                      analysisTimes = trial_duration,
                      events = .1) 

  tab_new <- tibble(`Study duration` = trial_duration,
                    N = FH05$analysis$N[1],
                    Events = FH05$analysi$Events[1], 
                    `Events/N` = Events/N, 
                    # we use the AHR from regular WLR as the AHR of different max combo test
                    AHR = as.numeric(FH00$analysis$AHR[1]), 
                    `FH(0, 0.5) power` = FH05$bounds$Probability[1],
                    `FH(0, 0) power` = FH00$bounds$Probability[1],
                    `MC2 power` = MC2$bounds$Probability[1],
                    `MC4 power` = MC4$bounds$Probability[1],
                    `MC3 power` = MC3$bounds$Probability[1],
                    `MB6 power` = MB6$bounds$Probability[1])

  tab <- rbind(tab, tab_new)
}

tab %>% 
  gt() %>%
  fmt_number(columns = c(2, 3), decimals = 1) %>%
  fmt_number(columns = 4, decimals = 2) %>%
  fmt_number(columns = 5, decimals = 4) %>%
  fmt_number(columns = 6:11, decimals = 2)


keaven/gsDesign2 documentation built on Oct. 13, 2022, 8:42 p.m.