Skip to main content

group-sequential-methods

Group sequential design methods for interim analyses, alpha spending, and futility stopping. Use when designing trials with interim looks or implementing spending functions.

Ir a la instalación

Datos de origen

Repositorio
choxos/ClinicalTrialAgent
Última actividad en el origen
10 de enero de 2026 a las 18:34
Idioma detectado de SKILL.md
inglés
Estrellas
0
Forks
0

Opciones de instalación

De forma predeterminada está seleccionado el prompt que primero revisa el origen. Puedes cambiar a un comando directo o descargar una copia local.

Revisa los archivos de origen

Lee SKILL.md y los archivos complementarios que muestra SkillsMP antes de decidir si quieres instalarlo.

Mostrando SKILL.md

SKILL.md
Instrucciones de origen · Vista previa de solo lectura
name
group-sequential-methods
description
Group sequential design methods for interim analyses, alpha spending, and futility stopping. Use when designing trials with interim looks or implementing spending functions.
# Group Sequential Methods ## When to Use This Skill - Designing group sequential trials with interim analyses - Implementing alpha spending functions - Setting futility stopping rules - Calculating information fractions - Using sim_gs_n() for GS simulations - Integrating with gsDesign2 package ## Fundamental Concepts ### Group Sequential Design A group sequential design allows for: - **Early stopping for efficacy**: If treatment effect is larger than expected - **Early stopping for futility**: If treatment effect is unlikely to reach significance - **Reduced expected sample size**: When treatment effect is present ### Information Fraction Information fraction at analysis k: ``` I_k / I_K = (events at analysis k) / (total planned events) ``` For time-to-event trials, information ≈ number of events. ### Type I Error Spending The key constraint: Σ α_k ≤ α (overall Type I error) Spending functions distribute alpha across analyses. ## Alpha Spending Functions ### O'Brien-Fleming (OBF) **Properties:** - Conservative at early analyses - Nearly full alpha at final analysis - Difficult to stop early - Maintains nominal Type I error **Formula:** ``` α*(t) = 2 - 2Φ(z_{α/2} / √t) ``` **When to Use:** - Want maximum power at final analysis - Early efficacy stopping unlikely - Regulatory preference for conservative early bounds ### Pocock **Properties:** - Equal spending at each analysis - Easier to stop early - Inflated final alpha - Lower power at final analysis **Formula:** ``` α*(t) = α × log(1 + (e-1)t) ``` **When to Use:** - Early stopping is a priority - Treatment effect expected to be large - Willing to sacrifice final analysis power ### Hwang-Shih-DeCani (HSD) **Properties:** - Flexible family indexed by γ - γ = -4: Similar to OBF - γ = 1: Similar to Pocock - γ = 0: Linear (Pocock-like) **Formula:** ``` α*(t) = α × (1 - e^{-γt}) / (1 - e^{-γ}) ``` **When to Use:** - Want flexibility between OBF and Pocock - Customized spending pattern needed ### Spending Function Comparison | Function | Early Spending | Final Power | Early Stopping | |----------|---------------|-------------|----------------| | OBF | Low | High | Difficult | | Pocock | High | Lower | Easier | | HSD(γ=-4) | Low | High | Difficult | | HSD(γ=1) | High | Lower | Easier | ## Futility Boundaries ### Binding Futility - If futility boundary crossed, trial MUST stop - Affects Type I error calculation - More powerful than non-binding ### Non-Binding Futility - Crossing futility boundary is advisory - Trial can continue at investigator discretion - Conservative: assumes no early stopping for futility in Type I error ### Beta-Spending for Futility Similar to alpha-spending, but for Type II error: ``` β*(t) = spending function × β ``` ## simtrial GS Implementation ### create_cut() - Define Analysis Timing ```r # Interim Analysis 1 ia1_cut <- create_cut( planned_calendar_time = 20, # Minimum 20 months target_event_overall = 100, # Target 100 events max_extension_for_target_event = 24, # Wait up to 24 months for events min_n_overall = 200, # At least 200 enrolled min_followup = 12 # 12 months minimum follow-up ) # Interim Analysis 2 ia2_cut <- create_cut( planned_calendar_time = 32, target_event_overall = 200, max_extension_for_target_event = 34, min_time_after_previous_analysis = 10 # At least 10 months after IA1 ) # Final Analysis fa_cut <- create_cut( planned_calendar_time = 45, target_event_overall = 350 ) ``` ### sim_gs_n() - Run GS Simulations ```r library(simtrial) library(gsDesign2) # Define enrollment enroll_rate <- define_enroll_rate( duration = c(4, 12), rate = c(10, 30) ) # Define failure rates fail_rate <- define_fail_rate( duration = c(3, 100), fail_rate = log(2)/9, hr = c(1, 0.6), dropout_rate = 0.001 ) # Run simulation results <- sim_gs_n( n_sim = 1000, sample_size = 400, enroll_rate = enroll_rate, fail_rate = fail_rate, test = wlr, cut = list(ia1 = ia1_cut, ia2 = ia2_cut, fa = fa_cut), weight = fh(rho = 0, gamma = 0) ) ``` ### Integration with gsDesign2 ```r library(gsDesign2) # Design with gsDesign2 design <- gs_design_ahr( enroll_rate = define_enroll_rate(duration = c(4, 12), rate = c(10, 30)), fail_rate = define_fail_rate( duration = c(3, 100), fail_rate = log(2)/9, hr = c(1, 0.6), dropout_rate = 0.001 ), alpha = 0.025, beta = 0.1, analysis_time = c(24, 36, 48), upper = gs_spending_bound, upar = list(sf = gsDesign::sfLDOF, total_spend = 0.025), lower = gs_spending_bound, lpar = list(sf = gsDesign::sfHSD, param = -4, total_spend = 0.1) ) |> to_integer() # Simulate with design object sim_results <- sim_gs_n( n_sim = 1000, sample_size = max(design$analysis$n), enroll_rate = design$enroll_rate, fail_rate = design$fail_rate, test = wlr, cut = NULL, # Auto-generated from design original_design = design, weight = fh(rho = 0, gamma = 0) ) ``` ### Bound Updates with sim_gs_n() When using `original_design`, sim_gs_n() can compute updated bounds: ```r # Results include planned and updated bounds results <- sim_gs_n( # ... parameters ... original_design = design, ia_alpha_spending = "min_planned_actual", # Conservative fa_alpha_spending = "full_alpha" # Spend full alpha at FA ) # Output includes: # - planned_upper_bound, planned_lower_bound # - updated_upper_bound, updated_lower_bound ``` **Alpha Spending Options:** | ia_alpha_spending | Description | |-------------------|-------------| | "min_planned_actual" | Conservative: min of planned and actual | | "actual" | Spend based on actual information | | fa_alpha_spending | Description | |-------------------|-------------| | "full_alpha" | Spend remaining alpha at final | | "info_frac" | Spend based on information fraction | ## Different Tests Across Analyses ```r # Different tests at each analysis ia1_test <- create_test(wlr, weight = fh(rho = 0, gamma = 0)) ia2_test <- create_test(wlr, weight = fh(rho = 0, gamma = 0.5)) fa_test <- create_test(wlr, weight = mb(delay = 6, w_max = Inf)) results <- sim_gs_n( n_sim = 1000, sample_size = 400, enroll_rate = enroll_rate, fail_rate = fail_rate, test = list(ia1 = ia1_test, ia2 = ia2_test, fa = fa_test), cut = list(ia1 = ia1_cut, ia2 = ia2_cut, fa = fa_cut) ) ``` ## Common GS Patterns ### Two-Look Design (1 IA + FA) ```r # IA at 50% information, FA at 100% ia_cut <- create_cut(target_event_overall = 150) # 50% fa_cut <- create_cut(target_event_overall = 300) # 100% sim_gs_n( n_sim = 1000, sample_size = 400, test = wlr, cut = list(ia = ia_cut, fa = fa_cut), weight = fh(0, 0) ) ``` ### Three-Look Design (2 IA + FA) ```r # Standard 33%, 67%, 100% information ia1_cut <- create_cut(target_event_overall = 100) ia2_cut <- create_cut(target_event_overall = 200) fa_cut <- create_cut(target_event_overall = 300) ``` ### Event-Driven with Calendar Constraints ```r # Events-based but with minimum calendar time ia_cut <- create_cut( target_event_overall = 150, planned_calendar_time = 18, # At least 18 months max_extension_for_target_event = 24 # Max 24 months ) ``` ## Operating Characteristics ### Key Metrics to Evaluate 1. **Power**: P(reject H0 | H1 true) 2. **Type I Error**: P(reject H0 | H0 true) 3. **Expected Sample Size**: E[N] under H0 and H1 4. **Expected Events**: E[events] at each analysis 5. **Stopping Probabilities**: P(stop at analysis k) ### Simulation Summary ```r # Summarize simulation results results_summary <- results |> group_by(analysis) |> summarise( mean_events = mean(event), mean_z = mean(z), power = mean(z < qnorm(0.025)), # One-sided .groups = "drop" ) ``` ## Best Practices 1. **Information Fraction**: Target evenly spaced (e.g., 50%, 100% or 33%, 67%, 100%) 2. **Alpha Spending**: OBF is default for most regulatory submissions 3. **Futility**: Use non-binding to preserve flexibility 4. **Validation**: Compare simulated power to gsDesign analytical results 5. **Documentation**: Record all boundary calculations for regulatory submission 6. **Parallelization**: Use `plan("multisession")` for large simulations ## Regulatory Considerations - Pre-specify number and timing of interim analyses - Pre-specify spending function and parameters - Document stopping rules clearly in protocol - Consider DSMB recommendations for unblinded reviews - Maintain blinding for operational team
Ver en GitHub