scikit-survival について
scikit-survival は、scikit-learn を基盤とする scikit-survival で生存分析を行うためのガイダンススキルです。打ち切りを含むイベント発生時間データを扱う分析者向けに、複数のモデルと打ち切りを考慮した評価方法を解説します。
主な機能
- 01打ち切り生存データの準備と検証
- 02Cox・アンサンブル・SVM モデルの適合
- 03Kaplan-Meier・Nelson-Aalen 曲線の推定
- 04打ち切り対応指標による評価
- 05競合リスクの分析
活用シーン
- 01打ち切り記録を含むイベント時間のモデル化
- 02生存モデル系列の比較
- 03打ち切りの多い条件での予測評価
- 04競合イベント別リスクの推定
インストール
コマンドをコピーしてターミナルで実行します。
npx skills add https:/ / github.com/ crazymsn/ academic-skills --skill scikit-survivalインストール後、Claude Code で/scikit-survivalを入力して読み込まれたか確認します。
同梱ファイル
SKILL.md と一緒にインストールされる参考資料やスクリプト。
references/competing-risks.mdcox-models.mddata-handling.mdensemble-models.mdevaluation-metrics.mdsvm-models.md詳細
scikit-survival: Python による生存時間解析
概要
scikit-survival は scikit-learn を基盤とした、生存時間解析のための Python ライブラリです。打ち切りデータ(観測値が部分的にしか分からないデータ)という特有の課題に対応する、時間-イベント解析向けの専用ツールを提供します。
生存時間解析は、共変量とイベント発生までの時間との関係を明らかにすることを目的とし、打ち切りされたレコード(特に、観察期間中にイベントが発生しなかった参加者を含む研究からの右側打ち切りデータ)を考慮します。
このスキルを使用する場面
次のような場合にこのスキルを使用してください:
- 生存時間解析または時間-イベントモデリングを行う場合
- 打ち切りデータ(右側打ち切り、左側打ち切り、区間打ち切り)を扱う場合
- Cox 比例ハザードモデル(標準または罰則付き)を当てはめる場合
- アンサンブル生存モデル(Random Survival Forests、Gradient Boosting)を構築する場合
- Survival Support Vector Machines を学習させる場合
- 生存モデルの性能(一致指数、Brier スコア、時間依存 AUC)を評価する場合
- Kaplan-Meier 曲線または Nelson-Aalen 曲線を推定する場合
- 競合リスクを分析する場合
- 生存データの前処理を行う場合、または生存データセットの欠損値を扱う場合
- scikit-survival ライブラリを用いたあらゆる分析を行う場合
中核となる機能
1. モデルの種類と選択
scikit-survival は、それぞれ異なる場面に適した複数のモデル群を提供します:
Cox 比例ハザードモデル
用途: 解釈可能な係数を持つ標準的な生存時間解析
CoxPHSurvivalAnalysis: 基本的な Cox モデルCoxnetSurvivalAnalysis: 高次元データ向けの弾性ネット罰則付き Cox モデルIPCRidge: 加速故障時間モデル向けの Ridge 回帰
参照: Cox モデル、正則化、解釈について詳しくは references/cox-models.md を参照してください
アンサンブル法
用途: 複雑な非線形関係に対する高い予測性能
RandomSurvivalForest: 頑健でノンパラメトリックなアンサンブル法GradientBoostingSurvivalAnalysis: 最大限の性能を目指す木ベースのブースティングComponentwiseGradientBoostingSurvivalAnalysis: 特徴量選択を伴う線形ブースティングExtraSurvivalTrees: 追加の正則化のための極度にランダム化された木
参照: アンサンブル法、ハイパーパラメータのチューニング、各モデルの使い分けについて詳しくは references/ensemble-models.md を参照してください
Survival Support Vector Machines
用途: マージンに基づく学習を行う中規模のデータセット
FastSurvivalSVM: 速度に最適化された線形 SVMFastKernelSurvivalSVM: 非線形関係向けのカーネル SVMHingeLossSurvivalSVM: ヒンジ損失を用いる SVMClinicalKernelTransform: 臨床データと分子データ向けの専用カーネル
参照: SVM の詳細、カーネルの選択、ハイパーパラメータのチューニングについては references/svm-models.md を参照してください
モデル選択の決定木
Start
├─ High-dimensional data (p > n)?
│ ├─ Yes → CoxnetSurvivalAnalysis (elastic net)
│ └─ No → Continue
│
├─ Need interpretable coefficients?
│ ├─ Yes → CoxPHSurvivalAnalysis or ComponentwiseGradientBoostingSurvivalAnalysis
│ └─ No → Continue
│
├─ Complex non-linear relationships expected?
│ ├─ Yes
│ │ ├─ Large dataset (n > 1000) → GradientBoostingSurvivalAnalysis
│ │ ├─ Medium dataset → RandomSurvivalForest or FastKernelSurvivalSVM
│ │ └─ Small dataset → RandomSurvivalForest
│ └─ No → CoxPHSurvivalAnalysis or FastSurvivalSVM
│
└─ For maximum performance → Try multiple models and compare
2. データの準備と前処理
モデリングの前に、生存データを適切に準備してください:
生存アウトカムの作成
from sksurv.util import Surv
# From separate arrays
y = Surv.from_arrays(event=event_array, time=time_array)
# From DataFrame
y = Surv.from_dataframe('event', 'time', df)
必須の前処理ステップ
- 欠損値の処理: 特徴量に対する補完戦略
- カテゴリ変数のエンコード: ワンホットエンコーディングまたはラベルエンコーディング
- 特徴量の標準化: SVM および正則化された Cox モデルにとって重要
- データ品質の検証: 負の時間の有無、特徴量ごとの十分なイベント数を確認
- 訓練・テストの分割: 分割間で打ち切り率が近くなるように維持
参照: 完全な前処理ワークフロー、データ検証、ベストプラクティスについては references/data-handling.md を参照してください
3. モデルの評価
生存モデルでは適切な評価が極めて重要です。打ち切りを考慮した適切な指標を使用してください:
一致指数(C-index)
順位付けおよび識別能力の主要な指標:
- Harrell の C-index: 打ち切り率が低い(40% 未満)場合に使用
- Uno の C-index: 中程度から高い打ち切り率(40% 超)の場合に使用 - より頑健
from sksurv.metrics import concordance_index_censored, concordance_index_ipcw
# Harrell's C-index
c_harrell = concordance_index_censored(y_test['event'], y_test['time'], risk_scores)[0]
# Uno's C-index (recommended)
c_uno = concordance_index_ipcw(y_train, y_test, risk_scores)[0]
時間依存 AUC
特定の時点における識別能力を評価します:
from sksurv.metrics import cumulative_dynamic_auc
times = [365, 730, 1095] # 1, 2, 3 years
auc, mean_auc = cumulative_dynamic_auc(y_train, y_test, risk_scores, times)
Brier Score
識別能力と校正の両方を評価します:
from sksurv.metrics import integrated_brier_score
ibs = integrated_brier_score(y_train, y_test, survival_functions, times)
参照: 包括的な評価ガイダンス、メトリクスの選択、交差検証でのスコアラーの使用方法については references/evaluation-metrics.md を参照してください
4. 競合リスク分析
互いに排他的な複数のイベントタイプが存在する状況を扱います:
from sksurv.nonparametric import cumulative_incidence_competing_risks
# Estimate cumulative incidence for each event type
time_points, cif_event1, cif_event2 = cumulative_incidence_competing_risks(y)
競合リスクを使用する場合:
- 互いに排他的な複数のイベントタイプが存在する場合(例: 異なる原因による死亡)
- あるイベントの発生が他のイベントの発生を妨げる場合
- 特定のイベントタイプの確率推定が必要な場合
参照: 詳細な競合リスクの手法、原因別ハザードモデル、解釈については references/competing-risks.md を参照してください
5. ノンパラメトリック推定
パラメトリックな仮定を置かずに生存関数を推定します:
Kaplan-Meier 推定量
from sksurv.nonparametric import kaplan_meier_estimator
time, survival_prob = kaplan_meier_estimator(y['event'], y['time'])
Nelson-Aalen 推定量
from sksurv.nonparametric import nelson_aalen_estimator
time, cumulative_hazard = nelson_aalen_estimator(y['event'], y['time'])
典型的なワークフロー
ワークフロー 1: 標準的な生存分析
from sksurv.datasets import load_breast_cancer
from sksurv.linear_model import CoxPHSurvivalAnalysis
from sksurv.metrics import concordance_index_ipcw
from sklearn.model_selection import train_test_split
from sklearn.preprocessing import StandardScaler
# 1. Load and prepare data
X, y = load_breast_cancer()
X_train, X_test, y_train, y_test = train_test_split(X, y, test_size=0.2, random_state=42)
# 2. Preprocess
scaler = StandardScaler()
X_train_scaled = scaler.fit_transform(X_train)
X_test_scaled = scaler.transform(X_test)
# 3. Fit model
estimator = CoxPHSurvivalAnalysis()
estimator.fit(X_train_scaled, y_train)
# 4. Predict
risk_scores = estimator.predict(X_test_scaled)
# 5. Evaluate
c_index = concordance_index_ipcw(y_train, y_test, risk_scores)[0]
print(f"C-index: {c_index:.3f}")
ワークフロー 2: 特徴選択を伴う高次元データ
from sksurv.linear_model import CoxnetSurvivalAnalysis
from sklearn.model_selection import GridSearchCV
from sksurv.metrics import as_concordance_index_ipcw_scorer
# 1. Use penalized Cox for feature selection
estimator = CoxnetSurvivalAnalysis(l1_ratio=0.9) # Lasso-like
# 2. Tune regularization with cross-validation
param_grid = {'alpha_min_ratio': [0.01, 0.001]}
cv = GridSearchCV(estimator, param_grid,
scoring=as_concordance_index_ipcw_scorer(), cv=5)
cv.fit(X, y)
# 3. Identify selected features
best_model = cv.best_estimator_
selected_features = np.where(best_model.coef_ != 0)[0]
ワークフロー 3: 最高性能を目指すアンサンブル手法
from sksurv.ensemble import GradientBoostingSurvivalAnalysis
from sklearn.model_selection import GridSearchCV
# 1. Define parameter grid
param_grid = {
'learning_rate': [0.01, 0.05, 0.1],
'n_estimators': [100, 200, 300],
'max_depth': [3, 5, 7]
}
# 2. Grid search
gbs = GradientBoostingSurvivalAnalysis()
cv = GridSearchCV(gbs, param_grid, cv=5,
scoring=as_concordance_index_ipcw_scorer(), n_jobs=-1)
cv.fit(X_train, y_train)
# 3. Evaluate best model
best_model = cv.best_estimator_
risk_scores = best_model.predict(X_test)
c_index = concordance_index_ipcw(y_train, y_test, risk_scores)[0]
ワークフロー 4: 包括的なモデル比較
from sksurv.linear_model import CoxPHSurvivalAnalysis
from sksurv.ensemble import RandomSurvivalForest, GradientBoostingSurvivalAnalysis
from sksurv.svm import FastSurvivalSVM
from sksurv.metrics import concordance_index_ipcw, integrated_brier_score
# Define models
models = {
'Cox': CoxPHSurvivalAnalysis(),
'RSF': RandomSurvivalForest(n_estimators=100, random_state=42),
'GBS': GradientBoostingSurvivalAnalysis(random_state=42),
'SVM': FastSurvivalSVM(random_state=42)
}
# Evaluate each model
results = {}
for name, model in models.items():
model.fit(X_train_scaled, y_train)
risk_scores = model.predict(X_test_scaled)
c_index = concordance_index_ipcw(y_train, y_test, risk_scores)[0]
results[name] = c_index
print(f"{name}: C-index = {c_index:.3f}")
# Select best model
best_model_name = max(results, key=results.get)
print(f"\nBest model: {best_model_name}")
scikit-learn との統合
scikit-survival は scikit-learn のエコシステムと完全に統合されています:
from sklearn.pipeline import Pipeline
from sklearn.preprocessing import StandardScaler
from sklearn.model_selection import cross_val_score, GridSearchCV
# Use pipelines
pipeline = Pipeline([
('scaler', StandardScaler()),
('model', CoxPHSurvivalAnalysis())
])
# Use cross-validation
scores = cross_val_score(pipeline, X, y, cv=5,
scoring=as_concordance_index_ipcw_scorer())
# Use grid search
param_grid = {'model__alpha': [0.1, 1.0, 10.0]}
cv = GridSearchCV(pipeline, param_grid, cv=5)
cv.fit(X, y)
ベストプラクティス
- SVM と正則化された Cox モデルでは、常に特徴量を標準化してください
- 打ち切り率が 40% を超える場合は、Harrell の C-index ではなく Uno の C-index を使用してください
- 複数の評価指標を報告してください(C-index、積分ブライアスコア、時間依存 AUC)
- Cox モデルでは比例ハザードの仮定を確認してください
- 適切なスコアラーを用いた交差検証により、ハイパーパラメータをチューニングしてください
- モデル化の前にデータ品質を検証してください(負の時間の有無、特徴量ごとに十分なイベント数があるかを確認)
- 複数のモデルタイプを比較し、最良の性能を見つけてください
- ランダム生存フォレストでは、組み込みの重要度ではなく順列重要度を使用してください
- 複数のイベントタイプが存在する場合は、競合リスクを考慮してください
- 分析では打ち切りの仕組みと打ち切り率を文書化してください
避けるべきよくある落とし穴
- 打ち切りが多い場合に Harrell の C-index を使用する → Uno の C-index を使用する
- SVM で特徴量を標準化しない → 必ず標準化する
- concordance_index_ipcw に y_train を渡し忘れる → IPCW の計算に必須
- 競合イベントを打ち切りとして扱う → 競合リスクの手法を使用する
- 特徴量ごとのイベント数を確認しない → 目安として、特徴量 1 つあたり 10 件以上のイベント
- RSF で組み込みの特徴量重要度を使用する → 順列重要度を使用する
- 比例ハザードの仮定を無視する → 仮定を検証するか、代替モデルを使用する
- 交差検証で適切なスコアラーを使用しない → as_concordance_index_ipcw_scorer() を使用する
参照ファイル
このスキルには、特定のトピックに関する詳細な参照ファイルが含まれています:
references/cox-models.md: Cox 比例ハザードモデル、ペナルティ付き Cox(CoxNet)、IPCRidge、正則化戦略、解釈に関する完全ガイドreferences/ensemble-models.md: ランダム生存フォレスト、勾配ブースティング、ハイパーパラメータチューニング、特徴量重要度、モデル選択references/evaluation-metrics.md: 一致指数(Harrell 版 vs Uno 版)、時間依存 AUC、ブライアスコア、包括的な評価パイプラインreferences/data-handling.md: データの読み込み、前処理ワークフロー、欠損データの扱い、特徴量エンコーディング、検証チェックreferences/svm-models.md: 生存サポートベクターマシン、カーネルの選択、臨床カーネル変換、ハイパーパラメータチューニングreferences/competing-risks.md: 競合リスク分析、累積発生関数、原因別ハザードモデル
特定のタスクで詳細な情報が必要な場合は、これらの参照ファイルを読み込んでください。
追加リソース
- 公式ドキュメント: https://scikit-survival.readthedocs.io/
- GitHub リポジトリ: https://github.com/sebp/scikit-survival
- 組み込みデータセット: 練習用データセット(GBSG2、WHAS500、退役軍人の肺がんデータなど)には
sksurv.datasetsを使用してください - API リファレンス: クラスと関数の完全な一覧は https://scikit-survival.readthedocs.io/en/stable/api/index.html を参照してください
クイックリファレンス: 主なインポート
# Models
from sksurv.linear_model import CoxPHSurvivalAnalysis, CoxnetSurvivalAnalysis, IPCRidge
from sksurv.ensemble import RandomSurvivalForest, GradientBoostingSurvivalAnalysis
from sksurv.svm import FastSurvivalSVM, FastKernelSurvivalSVM
from sksurv.tree import SurvivalTree
# Evaluation metrics
from sksurv.metrics import (
concordance_index_censored,
concordance_index_ipcw,
cumulative_dynamic_auc,
brier_score,
integrated_brier_score,
as_concordance_index_ipcw_scorer,
as_integrated_brier_score_scorer
)
# Non-parametric estimation
from sksurv.nonparametric import (
kaplan_meier_estimator,
nelson_aalen_estimator,
cumulative_incidence_competing_risks
)
# Data handling
from sksurv.util import Surv
from sksurv.preprocessing import OneHotEncoder, encode_categorical
from sksurv.datasets import load_gbsg2, load_breast_cancer, load_veterans_lung_cancer
# Kernels
from sksurv.kernels import ClinicalKernelTransform