Main Content

cvpartition

교차 검증을 위한 데이터 분할

설명

cvpartition은 데이터 세트에 대한 임의 분할을 정의합니다. 이 분할을 사용하여 교차 검증을 통해 통계 모델을 검증하기 위한 훈련 세트와 검정 세트를 정의할 수 있습니다. training을 사용하여 훈련 인덱스를 추출하고 test를 사용하여 교차 검증을 위한 검정 인덱스를 추출합니다. repartition을 사용하여 주어진 cvpartition 객체와 동일한 유형의 새 임의 분할을 정의합니다.

생성

설명

c = cvpartition(n,"KFold",k)n개 관측값에 대한 k겹 교차 검증에 사용할 층화되지 않은 임의 분할을 정의하는 cvpartition 객체 c를 반환합니다. 이 분할은 관측값을 각각 관측값 개수가 거의 같은 k개의 서로소 부표본 또는 겹으로 임의로 나눕니다.

예제

c = cvpartition(n,"Holdout",p)n개의 관측값에 대한 홀드아웃 검증에 사용할 층화되지 않은 임의 분할을 생성합니다. 이 분할은 관측값을 훈련 세트 하나와 검정(홀드아웃) 세트 하나로 분할합니다.

예제

c = cvpartition(group,"KFold",k)는 층화된 k겹 교차 검증에 사용할 임의 분할을 생성합니다. 각 부표본 또는 겹은 관측값 개수가 거의 같으며 클래스 비율이 group에서의 클래스 비율과 거의 같습니다.

group을 첫 번째 입력 인수로 지정하면 cvpartitiongroup의 누락값에 대응되는 관측값 행을 버립니다.

예제

c = cvpartition(group,"KFold",k,"Stratify",stratifyOption)k겹 교차 검증을 위한 임의 분할을 정의하는 cvpartition 객체 c를 반환합니다. "Stratify",false를 지정하는 경우, cvpartitiongroup의 클래스 정보를 무시하고 층화되지 않은 임의 분할을 생성합니다. 그렇지 않은 경우, 기본적으로 층화가 구현됩니다.

c = cvpartition(group,"Holdout",p)group의 클래스 정보를 사용하여 관측값을 층화된 훈련 세트 하나와 검정(홀드아웃) 세트 하나로 임의로 분할합니다. 훈련 세트와 검정 세트 모두 클래스 비율이 group에서의 클래스 비율과 거의 같습니다.

예제

c = cvpartition(group,"Holdout",p,"Stratify",stratifyOption)은 임의 분할을 훈련 세트 하나와 검정(홀드아웃) 세트 하나로 정의하는 객체 c를 반환합니다. "Stratify",false를 지정하는 경우, cvpartition은 층화되지 않은 임의 분할을 생성합니다. 그렇지 않은 경우, 기본적으로 층화가 구현됩니다.

예제

c = cvpartition(n,"Leaveout")n개의 관측값에 대한 리브-원-아웃 교차 검증에 사용할 임의 분할을 생성합니다. 리브-원-아웃은 "KFold"의 특수한 사례로, 겹의 개수가 관측값 개수와 같습니다.

c = cvpartition(n,"Resubstitution")은 데이터를 분할하지 않는 객체 c를 생성합니다. 훈련 세트와 검정 세트 모두 n개의 원래 관측값 전체를 포함합니다.

예제

c = cvpartition("CustomPartition",testSets)testSets로 표시된 검정 세트에 따라 데이터를 분할하는 cvpartition 객체 c를 생성합니다. (R2023b 이후)

입력 인수

모두 확장

표본 데이터의 관측값 개수로, 양의 정수 스칼라로 지정됩니다.

예: 100

데이터형: single | double

분할에 포함된 겹의 개수로, 양의 정수 스칼라로 지정됩니다. k는 총 관측값 개수보다 작아야 합니다.

예: 5

데이터형: single | double

홀드아웃 검증에 사용된 검정 세트의 관측값 비율 또는 개수로, 범위 (0,1)의 스칼라 또는 범위 [1,n)의 정수 스칼라로 지정됩니다. 여기서 n은 총 관측값 개수입니다.

  • p가 범위 (0,1)의 스칼라인 경우, cvpartition은 검정 세트에 대해 대략 p*n개의 관측값을 임의로 선택합니다.

  • p가 범위 [1,n)의 정수 스칼라인 경우, cvpartition은 검정 세트에 대해 p개의 관측값을 임의로 선택합니다.

예: 0.2

예: 50

데이터형: single | double

층화를 위한 그룹화 변수로, 각 관측값의 클래스를 나타내는 숫자형 벡터 또는 논리형 벡터, categorical형 배열, 문자형 배열 또는 string형 배열 또는 문자형 벡터로 구성된 셀형 배열로 지정됩니다. cvpartitiongroup의 관측값에서 분할을 생성합니다.

데이터형: single | double | logical | categorical | char | string | cell

층화 표시자로, true 또는 false로 지정됩니다.

  • cvpartition에 대한 첫 번째 입력 인수가 group인 경우, cvpartition은 기본적으로 층화를 구현합니다("Stratify",true). 층화되지 않은 임의 분할의 경우, "Stratify",false를 지정하십시오.

  • cvpartition에 대한 첫 번째 입력 인수가 n인 경우, cvpartition은 항상 층화되지 않은 임의 분할을 생성합니다("Stratify",false). 이 경우, "Stratify",true를 지정할 수 없습니다.

데이터형: logical

R2023b 이후

사용자 지정 검정 세트로, 양의 정수 벡터, 논리형 벡터 또는 논리형 행렬로 지정됩니다.

  • 홀드아웃 검증의 경우, 논리형 벡터를 사용하여 검정 세트 관측값을 지정합니다. 값 1(true)은 대응되는 관측값이 검정 세트에 있음을 나타내고, 값 0(false)은 대응되는 관측값이 훈련 세트에 있음을 나타냅니다.

  • k겹 교차 검증의 경우, 정수 벡터(범위 [1,k] 내에 있는 값을 가짐) 또는 k개 열을 가진 논리형 행렬을 사용하여 검정 세트 관측값을 지정합니다.

    • 정수 벡터 — 값 j는 대응되는 관측값이 검정 세트 j에 있음을 나타냅니다.

    • 논리형 행렬 — 행 i와 열 j에 있는 값은 관측값 i가 검정 세트 j에 있는지 여부를 나타냅니다.

    각각의 k 검정 세트는 적어도 하나의 관측값을 포함해야 합니다.

  • 리브-원-아웃 교차 검증의 경우, 정수 벡터(범위 [1,n] 내에 있는 값을 가짐) 또는 n×n 논리형 행렬(여기서 n은 데이터에 있는 관측값 개수임)을 사용하여 검정 세트 관측값을 지정합니다.

    • 정수 벡터 — 값 j는 대응되는 관측값이 검정 세트 j에 있음을 나타냅니다.

    • 논리형 행렬 — 행 i와 열 j에 있는 값은 관측값 i가 검정 세트 j에 있는지 여부를 나타냅니다.

예: "CustomPartition",[true false true false false]는 첫 번째, 세 번째 관측값이 검정 세트에 있는 홀드아웃 검증 방식을 나타냅니다.

예: "CustomPartition",[1 2 2 1 3 3 1 2 3 2]는 첫 번째, 네 번째, 일곱 번째 관측값이 첫 번째 검정 세트에 있는 3겹 교차 검증 방식을 나타냅니다.

데이터형: single | double | logical

속성

모두 확장

R2023b 이후

읽기 전용 속성입니다.

사용자 지정 분할의 표시자로, 논리형 스칼라로 지정됩니다. 객체가 사용자 지정 분할을 사용하여 생성된 경우, 값은 1(true)입니다. 그렇지 않으면 값은 0(false)입니다.

데이터형: logical

읽기 전용 속성입니다.

누락된 group 값을 갖는 관측값을 포함한 관측값 개수로, 양의 정수 스칼라로 지정됩니다.

데이터형: double

읽기 전용 속성입니다.

분할의 총 검정 세트 개수로, 분할 유형이 'kfold' 또는 'leaveout'인 경우 겹의 개수로 지정되고, 분할 유형이 'holdout' 또는 'resubstitution'인 경우 1로 지정됩니다.

데이터형: double

읽기 전용 속성입니다.

각 검정 세트의 크기로, 분할 유형이 'kfold' 또는 'leaveout'인 경우 양의 정수 벡터로 지정되고, 분할 유형이 'holdout' 또는 'resubstitution'인 경우 양의 정수 스칼라로 지정됩니다.

데이터형: double

읽기 전용 속성입니다.

각 훈련 세트의 크기로, 분할 유형이 'kfold' 또는 'leaveout'인 경우 양의 정수 벡터로 지정되고, 분할 유형이 'holdout' 또는 'resubstitution'인 경우 양의 정수 스칼라로 지정됩니다.

데이터형: double

읽기 전용 속성입니다.

검증 분할의 유형으로, 'kfold', 'holdout', 'leaveout' 또는 'resubstitution'으로 지정됩니다.

객체 함수

repartitionRepartition data for cross-validation
test교차 검증을 위한 검정 인덱스
training교차 검증을 위한 훈련 인덱스

예제

모두 축소

교차 검증 오분류 오차를 사용하여 새 데이터에 대한 모델의 성능을 추정합니다.

ionosphere 데이터 세트를 불러옵니다. 예측 변수 데이터 X와 응답 변수 Y를 포함하는 테이블을 생성합니다.

load ionosphere
tbl = array2table(X);
tbl.Y = Y;

층화되지 않은 임의 분할 hpartition을 사용하여 데이터를 훈련 데이터(tblTrain)와 나중에 사용할 데이터 세트(tblNew)로 분할합니다. 데이터의 약 30%를 따로 남겨둡니다.

rng('default') % For reproducibility
n = length(tbl.Y);
hpartition = cvpartition(n,'Holdout',0.3); % Nonstratified partition
idxTrain = training(hpartition);
tblTrain = tbl(idxTrain,:);
idxNew = test(hpartition);
tblNew = tbl(idxNew,:);

훈련 데이터 tblTrain을 사용하여 서포트 벡터 머신(SVM) 분류 모델을 훈련시킵니다. 훈련 데이터에 대한 오분류 오차와 분류 정확도를 계산합니다.

Mdl = fitcsvm(tblTrain,'Y');
trainError = resubLoss(Mdl)
trainError = 0.0569
trainAccuracy = 1-trainError
trainAccuracy = 0.9431

일반적으로, 훈련 데이터에 대한 오분류 오차는 새 데이터에 대한 모델의 성능을 추정하기에 좋은 척도가 아닙니다. 새 데이터에 대한 오분류율을 과소평가할 수 있기 때문입니다. 보다 효과적인 척도는 교차 검증 오차입니다.

분할된 모델 cvMdl을 생성합니다. 10겹 교차 검증 오분류 오차와 분류 정확도를 계산합니다. 기본적으로, crossval은 각 겹의 클래스 비율이 응답 변수 tblTrain.Y의 클래스 비율과 거의 동일하게 유지되도록 합니다.

cvMdl = crossval(Mdl); % Performs stratified 10-fold cross-validation
cvtrainError = kfoldLoss(cvMdl)
cvtrainError = 0.1220
cvtrainAccuracy = 1-cvtrainError
cvtrainAccuracy = 0.8780

교차 검증 오차 cvtrainError가 재대입 오차 trainError보다 크다는 점에 유의하십시오.

훈련된 SVM 모델을 사용하여 tblNew에 있는 새 데이터를 분류합니다. 새 데이터에 대한 분류 정확도를 정확도 추정값 trainAccuracycvtrainAccuracy와 비교합니다.

newError = loss(Mdl,tblNew,'Y');
newAccuracy = 1-newError
newAccuracy = 0.8700

새 데이터에서 교차 검증 오차가 재대입 오차보다 더 효과적으로 모델 성능을 추정합니다.

5겹 교차 검증에 층화된 동일한 분할을 사용하여 두 모델의 오분류율을 계산합니다.

fisheriris 데이터 세트를 불러옵니다. 행렬 meas는 150개의 서로 다른 꽃에 대한 꽃 측정치를 포함합니다. 변수 species는 각 꽃의 종을 나열합니다.

load fisheriris

층화된 5겹 교차 검증에 사용할 임의 분할을 생성합니다. 훈련 세트와 검정 세트는 대략적으로 species와 동일한 비율의 꽃 종을 가집니다.

rng('default') % For reproducibility
c = cvpartition(species,'KFold',5);

c를 사용해 분할된 판별분석 모델과 분할된 분류 트리 모델을 생성합니다.

discrCVModel = fitcdiscr(meas,species,'CVPartition',c);
treeCVModel = fitctree(meas,species,'CVPartition',c);

두 개의 분할된 모델의 오분류율을 계산합니다.

discrRate = kfoldLoss(discrCVModel)
discrRate = 0.0200
treeRate = kfoldLoss(treeCVModel)
treeRate = 0.0333

판별분석 모델의 교차 검증 오분류율이 더 작습니다.

fisheriris 데이터의 층화되지 않은 5겹 분할에서 검정 세트(겹) 클래스 비율을 관측합니다. 클래스 비율은 겹마다 다릅니다.

fisheriris 데이터 세트를 불러옵니다. species 변수는 각 꽃(관측값)에 대한 종 이름(클래스)을 포함합니다. speciescategorical형 변수로 변환합니다.

load fisheriris
species = categorical(species);

각 클래스에서 관측값의 개수를 구합니다. 세 클래스가 동일한 비율로 발생합니다.

C = categories(species) % Class names
C = 3x1 cell
    {'setosa'    }
    {'versicolor'}
    {'virginica' }

numClasses = size(C,1);
n = countcats(species) % Number of observations in each class
n = 3×1

    50
    50
    50

층화되지 않은 5겹 임의 분할을 생성합니다.

rng('default') % For reproducibility
cv = cvpartition(species,'KFold',5,'Stratify',false) 
cv = 
K-fold cross validation partition
   NumObservations: 150
       NumTestSets: 5
         TrainSize: 120  120  120  120  120
          TestSize: 30  30  30  30  30
          IsCustom: 0

세 클래스가 5개의 검정 세트(또는 겹)에서 동일한 비율로 발생하지 않는 것을 확인해 보겠습니다. for 루프를 사용하여 각 요소 nTestData(i,j)가 검정 세트 i 및 클래스 C(j)의 관측값 개수에 대응하도록 nTestData 행렬을 업데이트합니다. nTestData의 데이터에서 막대 차트를 생성합니다.

numFolds = cv.NumTestSets;
nTestData = zeros(numFolds,numClasses);
for i = 1:numFolds
    testClasses = species(cv.test(i));
    nCounts = countcats(testClasses); % Number of test set observations in each class
    nTestData(i,:) = nCounts';
end

bar(nTestData)
xlabel('Test Set (Fold)')
ylabel('Number of Observations')
title('Nonstratified Partition')
legend(C)

Figure contains an axes object. The axes object with title Nonstratified Partition, xlabel Test Set (Fold), ylabel Number of Observations contains 3 objects of type bar. These objects represent setosa, versicolor, virginica.

클래스 비율이 일부 검정 세트에서 다르게 나타납니다. 예를 들어, 첫 번째 검정 세트에는 종마다 10송이씩 있는 것이 아니라 setosa 8송이, versicolor 13송이, virginica 9송이가 포함되어 있습니다. cvfisheriris 데이터의 층화되지 않은 임의 분할이기 때문에 검정 세트(겹) 각각마다 클래스 비율이 species의 클래스 비율과 같다는 보장이 없습니다. 즉, 각각의 검정 세트에서는 species에서처럼 클래스가 동일하게 나타나지 않습니다.

tall형 배열에 대해 층화되지 않은 홀드아웃 분할과 층화된 홀드아웃 분할을 생성합니다. 두 개의 홀드아웃 세트에 대해, 각 클래스의 관측값 개수를 비교합니다.

tall형 배열에서 계산을 수행할 때, MATLAB®은 병렬 풀(Parallel Computing Toolbox™를 사용할 경우 디폴트 값) 또는 로컬 MATLAB 세션을 사용합니다. Parallel Computing Toolbox가 있는 상태에서 로컬 MATLAB 세션을 사용하여 예제를 실행하려면 mapreducer 함수를 사용하여 전역 실행 환경을 변경하십시오.

mapreducer(0)

두 개의 클래스로 구성된 숫자형 벡터를 생성합니다. 여기서 클래스 1과 클래스 21:10 비율로 나타납니다.

group = [ones(20,1);2*ones(200,1)]
group = 220×1

     1
     1
     1
     1
     1
     1
     1
     1
     1
     1
      ⋮

group에서 tall형 배열을 생성합니다.

tgroup = tall(group)
tgroup =

  220x1 tall double column vector

     1
     1
     1
     1
     1
     1
     1
     1
     :
     :

Holdout은 tall형 배열에 지원되는 유일한 cvpartition 옵션입니다. 층화되지 않은 홀드아웃 임의 분할을 생성합니다.

CV0 = cvpartition(tgroup,'Holdout',1/4,'Stratify',false)  
CV0 = 
Hold-out cross validation partition
   NumObservations: [1x1 tall]
       NumTestSets: 1
         TrainSize: [1x1 tall]
          TestSize: [1x1 tall]
          IsCustom: 0

gather 함수를 사용하여 CV0.test의 결과를 메모리에 반환합니다.

testIdx0 = gather(CV0.test);
Evaluating tall expression using the Local MATLAB Session:
- Pass 1 of 1: Completed in 0.29 sec
Evaluation completed in 0.4 sec

각 클래스가 검정(즉, 홀드아웃) 세트에 나타나는 횟수를 구합니다.

accumarray(group(testIdx0),1) % Number of observations per class in the holdout set
ans = 2×1

     5
    51

cvpartition을 사용하면 결과가 임의성을 띠게 되므로 각 클래스의 관측값 개수가 여기에 표시된 결과와 다를 수 있습니다.

CV0은 층화되지 않은 분할이기 때문에 홀드아웃 세트에서 클래스 1 관측값과 클래스 2 관측값이 tgroup에서와 같은 비율로 나타난다는 보장이 없습니다. 하지만, cvpartition의 내재된 임의성으로 인해, 'Stratify',false를 지정하더라도 홀드아웃 세트에서 클래스가 tgroup에서와 같은 비율로 나타나는 경우가 있습니다. 훈련 세트는 홀드아웃 세트의 보수이므로, NaN 또는 누락 관측값을 제외시켜 훈련 세트에 대해 유사한 결과를 얻을 수 있습니다.

CV0.training의 결과를 메모리에 반환합니다.

trainIdx0 = gather(CV0.training);
Evaluating tall expression using the Local MATLAB Session:
- Pass 1 of 1: Completed in 0.097 sec
Evaluation completed in 0.14 sec

훈련 세트에서 각 클래스가 나타나는 횟수를 구합니다.

accumarray(group(trainIdx0),1) % Number of observations per class in the training set
ans = 2×1

    15
   149

층화되지 않은 훈련 세트의 클래스는 tgroup에서와 같은 비율로 나타난다는 보장이 없습니다.

층화된 홀드아웃 임의 분할을 생성합니다.

CV1 = cvpartition(tgroup,'Holdout',1/4)  
CV1 = 
Hold-out cross validation partition
   NumObservations: [1x1 tall]
       NumTestSets: 1
         TrainSize: [1x1 tall]
          TestSize: [1x1 tall]
          IsCustom: 0

CV1.test의 결과를 메모리에 반환합니다.

testIdx1 = gather(CV1.test);
Evaluating tall expression using the Local MATLAB Session:
- Pass 1 of 1: Completed in 0.12 sec
Evaluation completed in 0.15 sec

각 클래스가 검정(즉, 홀드아웃) 세트에 나타나는 횟수를 구합니다.

accumarray(group(testIdx1),1) % Number of observations per class in the holdout set
ans = 2×1

     5
    51

층화된 홀드아웃 분할의 경우 홀드아웃 세트의 클래스 비율과 tgroup의 클래스 비율은 동일하게 (1:10)입니다.

리브-원-아웃 교차 검증을 위해 임의의 데이터 분할을 생성합니다. 훈련 세트 평균을 계산하고 비교합니다. 어떤 반복에서 평균이 크게 다르게 나올 경우 영향 관측값이 존재함을 의미합니다.

어느 한 값이 나머지 다른 값들보다 훨씬 큰 데이터 세트 X를 생성합니다.

X = [1 2 3 4 5 6 7 8 9 20]';

관측값이 10개이고 훈련 데이터와 검정 데이터의 반복이 10회인 cvpartition 객체를 생성합니다. cvpartition은 각 반복마다 훈련 세트에서 제외할 관측값을 한 개 선택하여 검정 세트용으로 남겨둡니다.

c = cvpartition(10,'Leaveout')
c = 
Leave-one-out cross validation partition
   NumObservations: 10
       NumTestSets: 10
         TrainSize: 9  9  9  9  9  9  9  9  9  9
          TestSize: 1  1  1  1  1  1  1  1  1  1
          IsCustom: 0

X에 리브-원-아웃 분할을 적용하고 crossval을 사용하여 각 반복에서 훈련 관측값의 평균을 취합니다.

values = crossval(@(Xtrain,Xtest)mean(Xtrain),X,'Partition',c)
values = 10×1

    6.5556
    6.4444
    7.0000
    6.3333
    6.6667
    7.1111
    6.8889
    6.7778
    6.2222
    5.0000

상자 차트(또는 상자 플롯)를 사용하여 훈련 세트 평균의 분포를 확인합니다. 플롯은 하나의 이상값을 표시합니다.

boxchart(values)

Figure contains an axes object. The axes object contains an object of type boxchart.

이상값에 대응하는 반복을 찾습니다. 해당 반복에서 검정 세트에 들어 있는 관측값을 찾습니다.

[~,repetitionIdx] = min(values)
repetitionIdx = 10
observationIdx = test(c,repetitionIdx);
influentialObservation = X(observationIdx)
influentialObservation = 20

이 관측값이 들어 있는 훈련 세트의 평균이 이 관측값이 없는 훈련 세트의 평균과 크게 다릅니다. 이렇게 큰 평균 변화는 X에서 값 20이 영향 관측값임을 나타냅니다.

사용자 지정 4겹 교차 검증 분할을 지정하여 교차 검증된 회귀 트리를 생성합니다.

carbig 데이터 세트를 불러옵니다. 응답 변수 MPG와 예측 변수 Acceleration, Cylinders 등을 포함하는 테이블 Tbl을 생성합니다.

load carbig
Tbl = table(Acceleration,Cylinders,Displacement, ...
    Horsepower,Model_Year,Weight,Origin,MPG);

누락값이 있는 관측값을 제거합니다. 누락값이 있는 관측값을 제거한 후 테이블 데이터의 크기를 확인합니다.

Tbl = rmmissing(Tbl);
dimensions = size(Tbl)
dimensions = 1×2

   392     8

결과로 생성된 테이블은 392개의 관측값을 포함하며, 392/4=98입니다.

Tbl 데이터의 사용자 지정 4겹 교차 검증 분할을 생성합니다. 처음 98개 관측값은 첫 번째 검정 세트에 배치하고, 그 다음 98개 관측값은 두 번째 검정 세트에 배치하는 식으로 수행합니다.

testSet = ones(98,1);
testIndices = [testSet; 2*testSet; ...
    3*testSet; 4*testSet];
c = cvpartition("CustomPartition",testIndices)
c = 
K-fold cross validation partition
   NumObservations: 392
       NumTestSets: 4
         TrainSize: 294  294  294  294
          TestSize: 98  98  98  98
          IsCustom: 1

사용자 지정 분할 c를 사용하여, 교차 검증된 회귀 트리를 훈련시킵니다. 모델 성능을 평가하기 위해 교차 검증 MSE(평균제곱오차)를 계산합니다.

cvMdl = fitrtree(Tbl,"MPG","CVPartition",c);
cvMSE = kfoldLoss(cvMdl)
cvMSE = 21.2223

  • groupcvpartition에 대한 첫 번째 입력 인수로 지정하는 경우, group에서 누락값에 대응되는 관측값 행이 버려집니다.

  • groupcvpartition에 대한 첫 번째 입력 인수로 지정하는 경우, 기본적으로 층화가 구현됩니다. "Stratify",false를 지정하여 층화되지 않은 임의 분할을 생성할 수 있습니다.

  • "Stratify",truecvpartition에 대한 첫 번째 입력 인수가 group인 경우에만 지정할 수 있습니다.

확장 기능

버전 내역

R2008a에 개발됨

모두 확장

참고 항목

| | |

도움말 항목