0
0

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?

閾値奏効率・期待奏効率からのサンプルサイズの計算

Posted at

ブラウザだけで使える無料統計ソフト Reactive stat では、様々なサンプルサイズの計算を提供しています。
そのうち、単一群(single-arm)の第Ⅱ相試験におけるサンプルサイズ の詳細をお示しいたします。
実際の計算は、下記 URL にウェブアプリを用意してあります。

image.png

解説

単一群(single-arm)の第Ⅱ相試験におけるサンプルサイズの計算について解説します。

閾値奏効率とは

この指標は、実用上重要であるとみなされる最小の奏効率を指します。すなわち、新しい治療法や薬が「有効である」と考えられる最低限必要な奏効率であり、これより低ければ効果がないと判断する値です。

期待奏効率とは

実際に実験や試験から期待される奏効率です。この値は、既存の予備データや過去の研究から導き出された値であり、このくらい効果が出てほしいという有効性を期待する値です。閾値奏効率よりも大きな値でなくてはなりません。

サンプルサイズについて

  • サンプルサイズは、実験の結果が有意であることを確認するために必要な被験者数や試行回数を示します。
  • 閾値奏効率と期待奏効率の差が大きい場合、必要なサンプルサイズは小さくなります。逆に、差が小さい場合、その差を検出するためにはより多くのサンプルが必要となります。
    • 差が大きいほど、効果の有無がはっきりと分かりやすいため、少ない人数でも判断できます。
    • 差が小さければ偶然による変動と真の効果を区別するために、より多くのデータが必要になります。

Simonの2段階デザインについて

第Ⅱ相試験にて、Simonの2段階デザインが用いらることがあります。これは、試験を2つのステージに分けて行うことで、早期に無効な治療法を中止し、有効な治療法を効率的に見出すことを目指すデザインです。

  1. 第1ステージ: まず少数の患者さんで試験を行い、効果を中間的に評価します。
  2. 第2ステージ: 第1ステージの結果が思わしくない場合(予め設定した基準を満たさない場合)、試験を早期に中止します。有望な場合は、第2ステージに進み、追加の患者さんで試験を継続し、最終的な効果を評価します。
  • Simonの2段階デザインを用いることで、無効な治療法を早期に見切り、不必要な患者さんへの治療を減らすことが期待できます。また、全体として必要な患者さんの数を減らし、試験を効率的に行うことが可能になります。

計算手順

まず簡単な式でサンプルサイズの目安を計算し、次に目標とする誤りの確率(実際は効果がないのに効果ありと判断する確率、効果があるのに効果なしと判断する確率)を考慮します。そして、誤りの確率が目標値以下になる最小のサンプルサイズを、二項分布を用いて探索的に決定します。

サンプルサイズの初期推定値の計算

$n = \lceil \frac{ ( z_{1-\alpha} \sqrt{p_0(1-p_0)} + z_{1-\beta} \sqrt{p_1(1-p_1)} )^2 }{ (p_1 - p_0)^2 } \rceil$

ここでの各項目の説明は次の通りです:

  • $p_0$: 閾値奏効率
  • $p_1$: 期待奏効率
  • $z_{1-\alpha}$: 有意水準 α での標準正規分布の上側確率点
  • $z_{1-\beta}$: 検出力 (1-β) での標準正規分布の上側確率点

サンプルサイズの探索

この初期推定値を基に、以下の条件を満たす最小の n とそれに対応する r を探索します:

  • 第 I 種の過誤 ($\alpha$): $P(X \geq r | n, p_0) \leq \alpha$
  • 第 II 種の過誤 ($\beta$): $P(X < r | n, p_1) \leq \beta$

ここで、X は二項分布 B(n, p) に従う確率変数です。

解析例

実際の計算例を示します。以下のパラメータを使用しました:

  • 閾値奏効率: 0.5
  • 期待奏効率: 0.6
  • α エラー: 0.05
  • 検出力 (1-βエラー): 0.8
  • 最大サンプルサイズ: 200 (Simonの2段階デザインで使用)

R コード

cat("#### 閾値奏効率・期待奏効率からのサンプルサイズの計算\n")
suppressMessages(library(clinfun))

message("\n\n#### Single-arm の第Ⅱ相臨床試験デザインのサンプルサイズ\nn: 必要症例数\nr: 治療の有効性が棄却されないために必要な奏功症例数\n")
ph2single(0.5, 0.6, 0.05, (1-0.8), nsoln=1)

message("\n\n#### Simonの最適およびミニマックス2段階デザインのサンプルサイズ\nn1, r1: 第1ステージ\nn, r: 全体")
ph2simon(0.5, 0.6, 0.05, (1-0.8), nmax=200)

R 結果

#### Single-arm の第Ⅱ相臨床試験デザインのサンプルサイズ
n: 必要症例数
r: 治療の有効性が棄却されないために必要な奏功症例数

    n  r Type I error Type II error
1 158 89     0.047237       0.19435

#### Simonの最適およびミニマックス2段階デザインのサンプルサイズ
n1, r1: 第1ステージ
n, r: 全体

 Simon 2-stage Phase II design 

Unacceptable response rate:  0.5 
Desirable response rate:  0.6 
Error rates: alpha =  0.05 ; beta =  0.2 

           r1  n1   r   n EN(p0) PET(p0)   qLo   qHi
Minimax    68 125  87 155  129.2  0.8585 0.775 1.000
Admissible 43  86  89 158  118.9  0.5429 0.736 0.775
Admissible 57 106  89 159  116.1  0.8089 0.720 0.736
Admissible 41  81  90 160  113.6  0.5878 0.624 0.720
Admissible 41  80  91 162  110.2  0.6312 0.513 0.624
Admissible 37  72  93 166  106.0  0.6380 0.332 0.513
Admissible 38  73  95 170  104.0  0.6800 0.323 0.332
Admissible 37  71  96 172  103.1  0.6823 0.236 0.323
Admissible 31  60  99 178  101.2  0.6506 0.074 0.236
Optimal    32  61 105 190  100.3  0.6955 0.000 0.074

この解析は R version 4.4.2 (2024-10-31) で実施しました。使用したパッケージは clinfun (1.1.3)、compiler (4.4.2)、mvtnorm (1.2-3) です。

結果の解釈

単一群の場合

必要症例数は158例で、治療の有効性が棄却されないために必要な奏功症例数は89例となりました。

Simonの2段階デザインの場合

複数のデザインオプションが提示されています:

  1. ミニマックスデザイン

    • 第1段階: 125例中68例
    • 全体: 155例中87例
    • 期待される症例数: 129.2
    • 試験中止確率: 0.8585
  2. 最適デザイン

    • 第1段階: 61例中32例
    • 全体: 190例中105例
    • 期待される症例数: 100.3
    • 試験中止確率: 0.6955

研究の制約条件に応じて、これらのデザインから適切なものを選択することができます。

Reactive stat における javascript での実装例

  • Single-arm の第Ⅱ相臨床試験デザインのサンプルサイズ計算です。
  • jStat.js ライブラリを利用しています。
  • Simonの最適およびミニマックス2段階デザインのサンプルサイズの計算は、javascript では実装していません。
function ph2single(p0, p1, alpha, beta) {
    // nの初期推定値を計算
    let nLower = Math.ceil((jStat.normal.inv(1 - alpha, 0, 1) ** 2 * p0 * (1 - p0) +
            jStat.normal.inv(1 - beta, 0, 1) ** 2 * p1 * (1 - p1)) /
        (p1 - p0) ** 2);
    let nUpper = nLower * 2; // 上限を初期推定値の2倍に設定

    let bestN = Infinity;
    let bestR = 0;
    let iteration = 0;
    const maxIterations = 400; // 最大反復回数

    while (nLower <= nUpper && iteration < maxIterations) {
        iteration++;
        let n = nLower; // 最小のnから探索を開始
        // console.log(`反復回数: ${iteration}, 探索範囲: [${nLower}, ${nUpper}], 現在のn: ${n}`);

        let minR = Math.max(0, Math.floor(n * p0));
        let maxR = Math.min(n, Math.ceil(n * p1));
        let foundSolution = false;

        for (let r = minR; r <= maxR; r++) {
            let typeIError = 1 - jStat.binomial.cdf(r - 1, n, p0);
            let typeIIError = jStat.binomial.cdf(r - 1, n, p1);

            if (typeIError <= alpha && typeIIError <= beta) {
                bestN = n;
                bestR = r;
                foundSolution = true;
                // console.log(`  解を発見: n = ${bestN}, r = ${bestR}`);
                break;
            }
        }

        if (foundSolution) {
            // 解が見つかった場合、探索を終了
            // console.log(`最適解が見つかりました。総反復回数: ${iteration}`);
            return {
                n: bestN,
                r: bestR - 1
            };
        } else {
            // 解が見つからない場合、nを増加
            nLower = n + 1;
        }

        // nUpperが非現実的に大きくなった場合、早期終了
        if (nLower > 10000) {
            // console.warn(`探索範囲が10000を超えました。探索を終了します。総反復回数: ${iteration}`);
            return {
                n: "N/A",
                r: "N/A"
            };
        }
    }

    // console.warn(`最大反復回数(${maxIterations})に達しましたが、解が見つかりませんでした。`);
    return {
        n: "収束せず",
        r: ""
    };
}

参考文献

0
0
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
0
0

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?