私には小さなコーパスがあり、10倍の交差検証を使用して単純なベイズ分類器の精度を計算したいと思います。
オプションは、これを自分でセットアップするか、NLTK 機械学習アルゴリズムの相互検証を直接サポートしない のように NLTK-Trainer のようなものを使用することです。
おそらく別のモジュールを使用してこれを行うことをお勧めしますが、本当に独自のコードを書きたい場合は、次のようなことができます。
10-foldが必要だとすると、トレーニングセットを10
サブセットに分割し、9/10
でトレーニングし、テストする必要があります残りの1/10
で、サブセットの組み合わせごとにこれを行います(10
)。
トレーニングセットがtraining
という名前のリストにあると仮定すると、これを達成する簡単な方法は次のようになります。
num_folds = 10
subset_size = len(training)/num_folds
for i in range(num_folds):
testing_this_round = training[i*subset_size:][:subset_size]
training_this_round = training[:i*subset_size] + training[(i+1)*subset_size:]
# train using training_this_round
# evaluate against testing_this_round
# save accuracy
# find mean accuracy over all rounds
実際、最も賛成の回答で提供される長いループの繰り返しは必要ありません。また、分類子の選択は無関係です(任意の分類子を使用できます)。
Scikitは cross_val_score を提供します。これは、すべてのループを内部で実行します。
from sklearn.cross_validation import KFold, cross_val_score
k_fold = KFold(len(y), n_folds=10, shuffle=True, random_state=0)
clf = <any classifier>
print cross_val_score(clf, X, y, cv=k_fold, n_jobs=1)
次のように、クロスバリデーションのためのnaivebayes sklearnにライブラリとNLTKの両方を使用しました。
import nltk
from sklearn import cross_validation
training_set = nltk.classify.apply_features(extract_features, documents)
cv = cross_validation.KFold(len(training_set), n_folds=10, indices=True, shuffle=False, random_state=None, k=None)
for traincv, testcv in cv:
classifier = nltk.NaiveBayesClassifier.train(training_set[traincv[0]:traincv[len(traincv)-1]])
print 'accuracy:', nltk.classify.util.accuracy(classifier, training_set[testcv[0]:testcv[len(testcv)-1]])
そして最後に平均精度を計算しました
Jaredの答え から着想を得て、ジェネレーターを使用したバージョンを以下に示します。
def k_fold_generator(X, y, k_fold):
subset_size = len(X) / k_fold # Cast to int if using Python 3
for k in range(k_fold):
X_train = X[:k * subset_size] + X[(k + 1) * subset_size:]
X_valid = X[k * subset_size:][:subset_size]
y_train = y[:k * subset_size] + y[(k + 1) * subset_size:]
y_valid = y[k * subset_size:][:subset_size]
yield X_train, y_train, X_valid, y_valid
データセットX
には、N個のデータポイント(例では4個)とD個の特徴(例では2個)があると仮定しています。関連するNラベルはy
に保存されます。
X = [[ 1, 2], [3, 4], [5, 6], [7, 8]]
y = [0, 0, 1, 1]
k_fold = 2
for X_train, y_train, X_valid, y_valid in k_fold_generator(X, y, k_fold):
# Train using X_train and y_train
# Evaluate using X_valid and y_valid
2番目の答えを変更しました:
cv = cross_validation.KFold(len(training_set), n_folds=10, shuffle=True, random_state=None)