Contenu connexe Plus de takehikoihayashi (12) 比例ハザードモデルはとってもtricky!1. 某勉強会資料 (2013.4.9) : テーマ「比例ハザードモデル」
比例ハザードモデルは
とってもtricky!
発表者:林岳彦
(国立環境研究所環境リスク研究センター)
13年4月9日火曜日 1
3. なぜ私@リスク学が比例ハザードモデルに興味があるのか
疫学者が言うところの 相対リスク って実は
いろんな指標を含むらしいことに薄々気がついてきた
Relative Risk!
Well, which one do you mean ??
Relative incident ratio
Standardized relative
Odds ratio
incident ratio (ex. SMR)
Hazard ratio
...中でも、 ハザード比 が今ひとつよく分からない!
その他の指標はまあ分からんでもない
(オッズ比を 相対リスク と呼ぶのは少しtrickyだと思うけど)
13年4月9日火曜日 3
4. さいしょの一歩:
(比例ハザードモデルにおける)
ハザード って何?
13年4月9日火曜日 4
5. ここで言われている「ハザード」とは?
どうやら「ハザード」とは生存時間解析(比例ハザード回帰などを含む)
において用いられる概念のようである...
で、どうやら「比例ハザード回帰」は、一般化線形モデルとのアナロジーで考えると:
ロジスティック回帰モデル
ハザード回帰モデル
ロジスティック回帰のlog(オッズ)の部分が
log(ハザード)に変わった形のものと考えられそうなんだけど...
(*誤差項の話はとりあえず無視)
だが、そもそもこの「ハザード」ってなんだ??
あと、「セミパラモデル」ってよく書いてあるけど具体的にはどういうこと??
13年4月9日火曜日 5
7. 「ハザード」の定義は?
「時間 t まで生存」の条件下で、次の瞬間に死亡が起こる確率
分かりにくい!
生存関数の傾き
ハザード関数
時間tまで生存する確率による条件付け
*ここで生存関数S(t)は時間 t まで生存する確率
大橋・浜田(1995)「生存時間解析」p19より
ハザード関数を理解するには、40歳死亡率とか50歳死亡率という概念を考
えれば分り易いかもしれない.すなわち40歳で死亡するためには40歳まで
生きている必要があり、そういう条件の下で次の1年間で死亡する確率が40
歳死亡率である.この1年間という時間の単位をどんどん短くし、ちょうど
自動車の走行距離から瞬間速度を求める場合のようにΔt→0の極限をとった
ものがハザード関数である
13年4月9日火曜日 7
8. 生存関数、ハザード関数、累積ハザード関数の関係
ハザード関数 累積ハザード関数 生存関数
大橋・浜田(1995)「生存時間解析」p20より引用
*これらの関数は数学的には互いに等価(相互変換可能)
等価なんだったら一番分かりやすい生存関数をベースにモデルを作ってくれればいいのに...Coxのいけず...
13年4月9日火曜日 8
9. どうやってデータからハザード関数を求めるの?
いろいろやり方はあるが、カプランマイヤー法というノンパラメトリックな方法により
とりあえず生存関数S(x)を求めるのが一般的らしい
i 回目のイベントにおける死亡数
i回目のイベント
直前の生存個体
の数
大橋・浜田(1995)
「生存時間解析」p33
より引用
でもこんな階段状関数になったら微分形であるハザード関数への換算の際に困るのでは?というところで混乱しちゃうんだけど...
13年4月9日火曜日 9
11. 「比例ハザードモデル」が使われるケース
基本的に「生存時間データ」の回帰分析に用いられる
what_a_dudeの日記「コックス回帰の位置づけと生存時間分析の基礎知識−コックス比例ハザードモデル(1)」より引用
http://d.hatena.ne.jp/what_a_dude/20120908/p1
13年4月9日火曜日 11
12. モデルのキモは「比例ハザード性」の仮定
比例ハザードモデルではハザード, 時間, 共変量の関係が
次のように表される
ベースラインハザード(ある基準となる共変量セットにおけるハザード)
時間t, 共変量(z1...zk)に 共変量(z1...zk)の値に
おけるハザードの値 依存したハザードの変化
ここはノンパラ ここはパラメトリック
(ex. カプランマイヤー法) (対数線形モデルを仮定)
合体して
セミパラメトリックモデル
trickyだよねえ...
13年4月9日火曜日 12
13. 比例ハザード性→ハザード比が時間に依存しない!
(例えば投薬あり:1、投薬なし:0とかを想像すると良いかも)
共変量 z1=1とz1=0 のハザードの比を計算してみると...
(*単純のためz1以外は平均値をとるとする)
ハザード比
= exp(偏回帰係数)
ハザードの比が時間 t に依存せずに常に一定!?
このかなり強い仮定( 比例ハザード性 )が
比例ハザードモデルのキモ!
13年4月9日火曜日 13
14. 回帰モデルのフィッティングは「部分尤度」に基づく
ここの部分しか考慮しない=「部分尤度」
*イベント順序のみを考えるだけならこの情報は不要
「ここの部分の値」が大きい→イベントが早く起こりやすい→
「ここの部分の値の大きさ」と「イベントが起きた順序」の不一致度が小さいほどよい
βと言えそう
言い換えると
「ある共変量z1...kのセットを持つ個体の順にイベントが起きた順序」の
尤度を最大とするβ1...kの値を求めることでβ1...kのフィッティングができる
総イベント数
p( Π i番目に死んだのが共変量z1...kのセットを持つ個体である確率|β1,...,βk)
i=1
たぶんこういう説明の仕方で正しいと思うんだけどものすごく自信があるわけではない...
13年4月9日火曜日 14
15. で、「部分尤度」に基づいて回帰係数を求めて計算終了...
あれれ?
回帰係数の計算の過程で一度もけっきょく
「ハザード関数の推定」してないよね??
比例ハザードモデルでは「ハザード関数の推定」を
すっとばしてハザード比の計算ができるのか...
(最初からそう言ってくれれば「カプランマイヤーの生存関数を推定しても階段状だから微分できないんですけど??
ハザード関数を算出するときに困ると思うんですけど??」とか心配する必要なんてなにもなかったのに!!!)
「ハザード関数をベースとする。だが推定は断る」的な...
うわーすげーtrickyだよなあこのモデル(遠い目)
13年4月9日火曜日 15
17. 今回用いるデータ: kidney dataとは
ポータブル腎臓カテーテル使用患者の
感染発生までの時間のデータ
(感染以外の原因でのカテーテル使用の終了あり→right censored data)
‘disease’
‘time’
疾病タイプ 感染発生までの時間
0=GN, 1=AN, 2=PKD, 3=Other
糸球体腎炎 多発性嚢胞腎
?急性の何か?
性別 年齢
‘sex’ ‘age’
13年4月9日火曜日 17
18. データを読み込んでみる
> install.packages('survival')
> install.packages('KMsurv')> library(survival)
> library(KMsurv)
> data(kidney, package = "survival")
> head(kidney)
id time status age sex disease frail
1 1 8 1 28 1 Other 2.3
2 1 16 1 28 1 Other 2.3
3 2 23 1 48 2 GN 1.9
4 2 13 0 48 2 GN 1.9
5 3 22 1 32 1 Other 1.2
6 3 28 1 32 1 Other 1.2
event(感染)は1, right censoredは0とコード化
13年4月9日火曜日 18
19. 生存時間解析用データへ変換しその中身を見てみる
> Surv(kidney$time,kidney$status)
[1] 8 16 23 13+ 22 28 447 318 30 12 24 245 7 9
[15] 511 30 53 196 15 154 7 333 141 8+ 96 38 149+ 70+
[29] 536 25+ 17 4+ 185 177 292 114 22+ 159+ 15 108+ 152 562
[43] 402 24+ 13 66 39 46+ 12 40 113+ 201 132
156 34 30
[57] 2 25 130 26 27 58 5+ 43 152 30 190 5+ 119 8
[71] 54+ 16+ 6+ 78 63 8+
time at eventが格納される.
+ はright censoredデータ
13年4月9日火曜日 19
20. カプランマイヤー法により生存関数を推定するぜ
> my.fit1 <- survfit(Surv(time,status) ~ disease, data=kidney)
> my.fit1
Call: survfit(formula = Surv(time, status) ~ disease, data = kidney)
records n.max n.start events median 0.95LCL 0.95UCL
disease=Other 26 26 26 20 141 30 318
disease=GN 18 18 18 14 30 25 NA
disease=AN 24 24 24 18 48 38 NA
disease=PKD 8 8 8 6 115 63 NA
疾病タイプで層別化された感染までの時間の
中央値と信頼区間を算出
13年4月9日火曜日 20
21. 得られる生存関数のプロットはこんなかんじ(全体プール)
> my.fit0 <- survfit(Surv(time,status), data=kidney)
> plot(my.fit0, main="Kaplan-Meier estimate", xlab="time", ylab="survival
function", col=1:4)
信頼区間も描いてくれます
13年4月9日火曜日 21
22. 得られる生存関数のプロットはこんなかんじ(疾病で層別)
> my.fit1 <- survfit(Surv(time,status) ~ disease, data=kidney)
> plot(my.fit1, main="Kaplan-Meier estimate", xlab="time", ylab="survival
function", col=1:4)
Other
GN
AN
PKD
層間に差がある?
13年4月9日火曜日 22
23. 得られる生存関数のプロットはこんなかんじ(性別で層別)
> my.fit2 <- survfit(Surv(time,status) ~ sex, data=kidney)
> plot(my.fit2, main="Kaplan-Meier estimate", xlab="time", ylab="survival
function", col=1:2)
Male
Female
明らかに男性の方が
感染の発生が速い
13年4月9日火曜日 23
24. いざ、比例ハザード回帰の実施!
> kidney.cox <- coxph(Surv(time,status) ~ sex + disease, data=kidney)
> summary(kidney.cox)
Call: 説明変数としてsexとdiseaseを指定
coxph(formula = Surv(time, status) ~ sex + disease, data = kidney)
n= 76, number of events= 58 ハザード比
coef exp(coef) se(coef) z Pr(>|z|) 基準は Others らしい
sex -1.4774 0.2282 0.3569 -4.140 3.48e-05 ***
diseaseGN 0.1392 1.1494 0.3635 0.383 0.7017
PKD と sex
diseaseAN 0.4132 1.5116 0.3360 1.230 0.2188 が有意にリスク
diseasePKD -1.3671 0.2549 0.5889 -2.321 0.0203 *
比が小さい
---
Signif. codes: 0 ‘***’ 0.001 ‘**’ 0.01 ‘*’ 0.05 ‘.’ 0.1 ‘ ’ 1
exp(coef) exp(-coef) lower .95 upper .95
sex 0.2282 4.3815 0.11339 0.4594
diseaseGN 1.1494 0.8700 0.56368 2.3437 あれ?
diseaseAN 1.5116 0.6616 0.78245 2.9202 生存関数のプロットと
diseasePKD 0.2549 3.9238 0.08035 0.8084
食い違ってるけど??
Concordance= 0.696 (se = 0.045 )
Rsquare= 0.206 (max possible= 0.993 )
Likelihood ratio test= 17.56 on 4 df, p=0.001501
Wald test = 19.77 on 4 df, p=0.0005533
Score (logrank) test = 19.97 on 4 df, p=0.0005069
13年4月9日火曜日 24
25. 得られる生存関数のプロット(疾病別:再掲)
> my.fit1 <- survfit(Surv(time,status) ~ disease, data=kidney)
> plot(my.fit1, main="Kaplan-Meier estimate", xlab="time", ylab="survival
function", col=1:4)
Other
GN
AN
PKD
OthersとPKDのプロットは
一番近いのになぜそこだけに有意差が?
13年4月9日火曜日 25
26. どうやら:シンプソンのパラドックス的状況の模様
disease による層別
> my.fit1 <- survfit(Surv(time,status) ~ disease, data=kidney)
> my.fit1
Call: survfit(formula = Surv(time, status) ~ disease, data = kidney)
records n.max n.start events median 0.95LCL 0.95UCL
disease=Other 26 26 26 20 141 30 318
disease=GN 18 18 18 14 30 25 NA
disease=AN 24 24 24 18 48 38 NA
disease=PKD 8 8 8 6 115 63 NA
disease+sex による層別 OthersとPKDの値は近い
> my.fit3 <- survfit(Surv(time,status) ~ disease + sex, data=kidney)
> my.fit3
Call: survfit(formula = Surv(time, status) ~ disease + sex, data = kidney)
records n.max n.start events median 0.95LCL 0.95UCL
disease=Other, sex=1 6 6 6 6 19 12 NA
disease=Other, sex=2 20 20 20 14 185 119 NA
disease=GN, sex=1 6 6 6 6 12 7 NA
disease=GN, sex=2 12 12 12 8 132 30 NA
disease=AN, sex=1 4 4 4 3 17 12 NA
disease=AN, sex=2 20 20 20 15 58 39 NA
disease=PKD, sex=1 4 4 4 3 152 63 NA
disease=PKD, sex=2 4 4 4 3 78 30 NA
交互作用もあるねこれ
サブ集団の割合の塩梅が差をマスクしてた模様
OthersとPKDの値は全然違う!
13年4月9日火曜日 26
27. いざ、比例ハザード回帰の実施!(再掲)
> kidney.cox <- coxph(Surv(time,status) ~ sex + disease, data=kidney)
> summary(kidney.cox)
Call: 説明変数としてsexとdiseaseを指定
coxph(formula = Surv(time, status) ~ sex + disease, data = kidney)
n= 76, number of events= 58 ハザード比
coef exp(coef) se(coef) z Pr(>|z|) 基準は Others らしい
sex -1.4774 0.2282 0.3569 -4.140 3.48e-05 ***
diseaseGN 0.1392 1.1494 0.3635 0.383 0.7017
PKD と sex
diseaseAN 0.4132 1.5116 0.3360 1.230 0.2188 が有意にリスク
diseasePKD -1.3671 0.2549 0.5889 -2.321 0.0203 *
比が小さい
---
Signif. codes: 0 ‘***’ 0.001 ‘**’ 0.01 ‘*’ 0.05 ‘.’ 0.1 ‘ ’ 1
exp(coef) exp(-coef) lower .95 upper .95
sex 0.2282 4.3815 0.11339 0.4594
diseaseGN 1.1494 0.8700 0.56368 2.3437 あれ?
diseaseAN 1.5116 0.6616 0.78245 2.9202 生存関数のプロットと
diseasePKD 0.2549 3.9238 0.08035 0.8084
食い違ってるけど??
Concordance= 0.696 (se = 0.045 )
Rsquare= 0.206 (max possible= 0.993 )
Likelihood ratio test= 17.56 on 4 df, p=0.001501
Wald test = 19.77 on 4 df, p=0.0005533 重回帰で交絡が調整されている
Score (logrank) test = 19.97 on 4 df, p=0.0005069 今回の解析がより妥当
13年4月9日火曜日 27
28. ちなみに:diseaseのみの層別化で仮説検定すると...
デフォルトだとMantel-Haenszel検定らしい
> survdiff(Surv(time,status) ~ disease, data=kidney)
Call:
survdiff(formula = Surv(time, status) ~ disease, data = kidney)
N Observed Expected (O-E)^2/E (O-E)^2/V
disease=Other 26 20 23.20 0.442 0.779
disease=GN 18 14 11.62 0.488 0.631
disease=AN 24 18 14.70 0.740 1.070
disease=PKD 8 6 8.48 0.724 0.989
有意差はまったく
検出できない
交絡の調整はとても大事ですね...
13年4月9日火曜日 28
29. 対数線形性を検証する(残差プロット)
パラメトリックな部分については対数線形性を
仮定しているのでその検証も必要
> scatter.smooth(residuals(kidney.cox,type="deviance"))
> abline(h=0,lty=3,col=2)
Deviance残差
バイアスに明らかな傾向はなさそう
13年4月9日火曜日 29
30. 比例ハザード性を検証する
スコア残差を用いた方法は以下(他にも色々方法あるらしいけど)
> kidney.phz <- cox.zph(kidney.cox)
> par(mfrow=c(2,2)) Scaled Schoenfeld残差というのと
> plot(kidney.phz,df=2) transformed survival timeの間の相関をみているらしい
rho chisq p
diseaseGN -0.05159 0.14339 0.705
diseaseAN 0.09068 0.45068 0.502
diseasePKD -0.00838 0.00425 0.948
GLOBAL NA 1.04211 0.791
有意差なし
(比例ハザード性は棄却できない)
13年4月9日火曜日 30
31. (おまけ)StepAICによる変数選択
交互作用もありそうなので冗長性の高いモデルから
StepAICでモデル選択してみよう 要はAICも適用可ってこと
kidney.cox2 <- coxph(formula = Surv(time,status) ~ (sex + disease + age)^2,
data=kidney)
kidney.cox2 StepAICで逐次的モデル選択
library(MASS);stepAIC(kidney.cox2) sex, disease, age
... (中略) について交互作用項
Df AIC
<none> 359.54 まで含めたフルモデルを作成
- sex:disease 3 366.24
Call: 最終的に得られたモデル
coxph(formula = Surv(time, status) ~ sex + disease + sex:disease,
data = kidney)
ハザード比
coef exp(coef) se(coef) z p
sex -2.525 8.00e-02 0.566 -4.462 8.1e-06
diseaseGN -1.342 2.61e-01 1.304 -1.029 3.0e-01
有意差のないものも
diseaseAN -1.418 2.42e-01 1.484 -0.956 3.4e-01
拾われているね
diseasePKD -7.382 6.22e-04 1.949 -3.787 1.5e-04
sex:diseaseGN 0.831 2.30e+00 0.760 1.093 2.7e-01 (それ自体は別にOKと思うよ)
sex:diseaseAN 1.075 2.93e+00 0.816 1.318 1.9e-01
sex:diseasePKD 4.214 6.77e+01 1.150 3.664 2.5e-04
↑リスク増加要因として交互作用(女性✕PKD)が挙げられている
Likelihood ratio test=30.3 on 7 df, p=8.5e-05 n= 76, number of events= 58
13年4月9日火曜日 31
32. (おまけ)パラメトリックモデルを用いた解析例
生存関数としてパラメトリックモデルを用いて
当てはめてみる
> survreg(Surv(time, status) ~ sex + disease, kidney, dist="weibull")
↑weibull分布を仮定
Call:
survreg(formula = Surv(time, status) ~ sex + disease, data = kidney,
dist = "weibull")
Coefficients:
(Intercept) sex diseaseGN diseaseAN diseasePKD
2.05010897 1.60606802 -0.08086843 -0.55800137 1.30838906
Scale= 0.9670717
Loglik(model)= -330.4 Loglik(intercept only)= -340.9
Chisq= 21.12 on 4 degrees of freedom, p= 3e-04
n= 76
13年4月9日火曜日 32
33. 質問がたくさんあります!
I have many questions!
*勉強会で議論した結果(?)を青色で追記しました(文責:林)
13年4月9日火曜日 33
34. 比例ハザード性なんて本当に成り立ってるの?
有意差ないからOK、とか言うけどさ、
応答の大きさに比べてノイズが大きいから検出できてないだけじゃないの?
生物学的/医学的なメカニズムから考えても、成り立つ場合が多いとは思えない
のだけれど...
厳密には成り立ってない場合でも「ロバストだからOK」、ってスタンスなの?
*「成り立ってない場合も普通に多いだろう」ということらしい
* 論文でlog-logプロットとか載っているのは稀だし、実務上そこはあまり深くは突っ込まれない模様
13年4月9日火曜日 34
35. 環境疫学において対数線形性ってどのくらい現実的なの?
特に説明変数に汚染物質の濃度を取る場合が気になる
放射線のLNTは線形だよね
まあ毒性試験でもロジスティック回帰つかうしねえ...(混乱してきた)
*ここはちょっと謎のまま
13年4月9日火曜日 35
36. 比例ハザード性みたいな強い仮定に基づくよりも
2時点のデータ使ったロジスティック回帰や
(aggregateしてカウントデータにして)ポワソン回帰の方が良くない?
シンプルにロジスティックやポアソン回帰じゃ駄目なの?
「時間情報が含まれてる」っていっても、比例ハザード性の仮定によって
結局それ全部捨ててないですか?
打ち切りデータの取り扱いとかが難しいってこと?
* 比例ハザードモデルでは「時間情報がある」と言っても、比例ハザード性のような強い仮定を前提にするこ
ととのトレードオフなので、そのメリットは微妙である
* 実際問題として、比例ハザード回帰よりも、ポワソン回帰のほうが良い場合も多い(一般化線形モデル共通
の豊富なtool boxを利用できる点でポワソン回帰の方が色々と取り回しが良い。例えば、ポワソン回帰のほう
が時間依存性共変量の取り込みなどが容易)
*「打ち切り」に関しては、ポワソン回帰でもオフセット項の導入により簡単に対応可能
* まあ、ポワソン回帰でも比例ハザード回帰でも解析結果は余り変わらない、という点ではどちらでも利用可
能のほうを使えばよい、とは言えるのかもしれない
13年4月9日火曜日 36
37. イベント発生数が多い時間帯に回帰全体が依存しがちでは?
それでいいっちゃいいんだけど...
モデルの結果を他集団に外挿するときに、とても気持ちわるい気もする
* 結局この辺りは、「比例ハザード性」がどれだけ成り立つのかどうかに依存する話である。(比例ハザード
性が成り立たない場合には、やっぱり気持ち悪い)
13年4月9日火曜日 37
38. ハザード比はサンプル集団の特性にどう依存する?
(例えば、サンプル集団の平均年齢)
例えば、平均年齢のみが異なる(その他の共変量は全く同一の)サンプル集団で
再度データを取り解析したら、同じハザード比が得られる?
* 結局この辺りは、「比例ハザード性」がどれだけ成り立つのかどうかに依存する話である。(比例ハザード
性が成り立たない場合には、やっぱり気持ち悪い)
13年4月9日火曜日 38
39. 比例ハザード回帰ではなぜグラフを描かないの?
連続変量に対する依存性に関してはグラフを描いてくれてもいいと思うの
* 説明変数に連続変量を用いるケース自体が稀なのかもしれない(比例ハザード回帰を用いるケースにおい
て、連続変量に対しての反応曲線全体を得たいというニーズがそもそも余りないっぽい)
13年4月9日火曜日 39
40. 「全死亡のハザード比が1.2」→「死亡者数が1.2倍になる」
と単純に解釈するのは間違い?
こう解釈できるときの条件は何かしら?
* 近似としてはそう解釈しても概ね構わないでしょう(*比例ハザードモデルの仮定が適応したい集団におい
て現実的に妥当ならば。モデルの外挿可能な範囲には注意が必要)
13年4月9日火曜日 40
41. ハザード比を絶対リスクに換算するにはどう計算する?
追加情報が必要だとしたら、何?
* 全死亡がエンドポイントの場合、標準化年齢別死亡率、計算したい都市における主要共変量の値、年齢区分
別人口数、があれば計算できそう
13年4月9日火曜日 41
42. 今回、参考にさせていただいた資料
Many thanks!
書籍 大橋・浜田(1995)「生存時間解析」 JPクライン・MLメシュベルガー「生存時間解析」
what_a_dudeさんが挙げていた 最初にこれ読んでちょっと混乱した。
本。とてもわかりやすかった。 翻訳のせいもある?
Web上の資料
(1)what_a_dudeの日記 http://d.hatena.ne.jp/what_a_dude/20120908/p1 など
「記事一覧」の検索窓から「比例ハザードモデル」で検索すると一連の記事が読めます。分かりやすいし面白いし数学的説明もちゃんとしてる。
(2)統計学入門 11.4 比例ハザードモデル http://www.snap-tck.com/room04/c01/stat/stat11/stat1104.html
比例ハザードモデルの解説。いろんなサイトを見ているとだんだん理解が立体的になってきます。
(3)Coxの比例ハザードモデルについて/土居正明 http://www012.upp.so-net.ne.jp/doi/biostat/CT39/Cox.pdf
一番やさしいレベルの解説かもしれない。最初はこれを読むのがオススメかも。
(4)Rと生存時間分析 http://mjin.doshisha.ac.jp/R/37/37.html
今回のRでの解析はほとんどこの内容に依拠しました。大変ありがとうございます。
(5)Cox回帰(比例ハザードモデル)/Action Potentials: 閾値以下 http://d.hatena.ne.jp/kay-j/20050908
Rでの解析例としてはここもオススメ。比例ハザード性の検証がきちんとやられてます。
(6)Survival Analysis in R - Statistics http://anson.ucdavis.edu/ hiwang/teaching/10fall/R_tutorial%201.pdf
UCLAの講義資料らしい。今回のRでの解析ではこれも参考にした。
13年4月9日火曜日 42