ROC/AUC 분석을 앞서 잠시 살펴봤는데, 이와 연관해서 사용할 수 있는 분석 방법 중 하나가 부트스트래핑 (bootstrapping)입니다. 이는 복원 추줄 방법으로 표본을 여러 차례 추출해 반복적으로 분석을 해 값을 추정하는 기법입니다. 간단한 설명을 아래에서 볼 수 있습니다.
역시 Pima 인디언 데이터로 간단히 살펴보겠습니다. ROC/AUC 분석과 관련해서는 pROC 패키지를 이용해서 부트스트래핑 분석을 시행할 수 있습니다. ci/auc/ci.coords 를 이용해서 혈압과 당뇨 발생의 상관성을 보겠습니다. (pressure=roc(pima$diabetes, pima$pressure, ci=TRUE)를 기준) boot.n 을 이용해서 부트스트랩 횟수를 정할 수 있습니다. auc/ci를 통해 AUC 값과 95% 신뢰구간을 구할 수 있습니다. ci.coords에서 x="best", input = "threshold" 를 지정하면 최적의 cutoff point를 찾습니다. 그리고 ret = c() 를 통해 cutoff point (threshold), 민감도 특이도를 구할 수 있습니다.
#boostrap
library(pROC)
library(mlbench)
data(PimaIndiansDiabetes)
pima <- pimaindiansdiabetes="" span="">->
pima<-subset pima="" pressure="">0)-subset>
pressure=roc(pima$diabetes, pima$pressure, ci=TRUE)
set.seed(1234)
ci(pressure, method = "bootstrap", boot.n = 1000)
auc(pressure, method = "bootstrap", boot.n = 1000)
ci.coords(pressure, x="best", input = "threshold", boot.n = 1000, ret=c("threshold","specificity", "sensitivity"))
> ci(pressure, method = "bootstrap", boot.n = 1000)
95% CI: 0.5654-0.649 (1000 stratified bootstrap replicates)
> auc(pressure, method = "bootstrap", boot.n = 1000)
Area under the curve: 0.6076
> ci.coords(pressure, x="best", input = "threshold", boot.n = 1000, ret=c("threshold","specificity", "sensitivity"))
95% CI (1000 stratified bootstrap replicates):
2.5% 50% 97.5%
threshold best: threshold 63.0000 69.0000 81.0000
threshold best: specificity 0.2660 0.4615 0.8191
threshold best: sensitivity 0.3373 0.7183 0.8849
>
민감도와 특이도의 합이 최대가 되는 최적의 cutoff point는 69라는 결론이 나왔습니다. 다만 AUC 값은 그다지 높지 않습니다. 이제 이를 훈련 데이터 (train)와 검증 데이터 (test)로 나눠 간단하게 검증해 보겠습니다.
set.seed(123)
sample_num = sample(1:nrow(pima), size = round(0.7 * nrow(pima)))
train = pima[ sample_num, ]
test = pima[ -sample_num, ]
pressure=roc(train$diabetes, train$pressure, ci=TRUE)
여기까지 샘플을 나눴습니다. 그 후에 훈련 데이터에서 부트스트랩을 구합니다.
set.seed(111)
ci(pressure, method = "bootstrap", boot.n = 1000)
auc(pressure, method = "bootstrap", boot.n = 1000)
ci.coords(pressure, x="best", input = "threshold", boot.n = 1000, ret=c("threshold","specificity", "sensitivity"))
여기서 나온 값인 69를 훈련 및 검증 데이터에서 표시해 줍니다.
plot.roc(train$diabetes, train$pressure,print.auc=FALSE,
ci=FALSE, col="black",lty=2,
print.thres=69)
legend(0.2,0.2, lty=1, legend=c("blood pressure"))
plot.roc(test$diabetes, test$pressure,print.auc=FALSE,
ci=FALSE, col="black",lty=2,
print.thres=69)
legend(0.2,0.2, lty=1, legend=c("blood pressure"))
실제 데이터 훈련과 검증은 상당히 복잡한 단계를 거쳐 이뤄질 수 있습니다. 사실 앞서 본 머신 러닝에서 흔히 사용하는 방법이기도 합니다. 여기서는 간단한 사례만 소개하고 나중에 다시 다뤄보겠습니다.
댓글
댓글 쓰기