|
| 1 | +import keras |
| 2 | +import numpy as np |
| 3 | +from keras import backend as K |
| 4 | +from keras.datasets import mnist |
| 5 | +from keras.models import Sequential |
| 6 | +from keras.layers import Dense, Dropout, Activation, Flatten, Conv2D, MaxPooling2D |
| 7 | +from keras.regularizers import l2 |
| 8 | +from keras.wrappers.scikit_learn import KerasClassifier |
| 9 | +from modAL.models import ActiveLearner |
| 10 | + |
| 11 | + |
| 12 | +def create_keras_model(): |
| 13 | + model = Sequential() |
| 14 | + model.add(Conv2D(32, (3, 3), activation='relu')) |
| 15 | + model.add(Conv2D(32, (3, 3), activation='relu')) |
| 16 | + model.add(MaxPooling2D(pool_size=(2, 2))) |
| 17 | + model.add(Dropout(0.25)) |
| 18 | + c = 3.5 |
| 19 | + weight_decay = c / float(X_train.shape[0]) |
| 20 | + model.add(Flatten()) |
| 21 | + model.add(Dense(128, activation='relu', kernel_regularizer=l2(weight_decay))) |
| 22 | + model.add(Dropout(0.5)) |
| 23 | + model.add(Dense(10, activation='softmax')) |
| 24 | + model.compile(loss='categorical_crossentropy', optimizer='adam', metrics=["accuracy"]) |
| 25 | + return model |
| 26 | + |
| 27 | + |
| 28 | +# create the classifier |
| 29 | +classifier = KerasClassifier(create_keras_model) |
| 30 | + |
| 31 | +# read training data |
| 32 | +(X_train, y_train), (X_test, y_test) = mnist.load_data() |
| 33 | + |
| 34 | + |
| 35 | +# assemble initial data |
| 36 | +initial_idx = np.array([],dtype=np.int) |
| 37 | +for i in range(10): |
| 38 | + idx = np.random.choice(np.where(y_train==i)[0], size=2, replace=False) |
| 39 | + initial_idx = np.concatenate((initial_idx, idx)) |
| 40 | + |
| 41 | +# Preprocessing |
| 42 | +X_train = X_train.reshape(60000, 28, 28, 1).astype('float32') / 255. |
| 43 | +X_test = X_test.reshape(10000, 28, 28, 1).astype('float32') / 255. |
| 44 | +y_train = keras.utils.to_categorical(y_train, 10) |
| 45 | +y_test = keras.utils.to_categorical(y_test, 10) |
| 46 | + |
| 47 | +X_initial = X_train[initial_idx] |
| 48 | +y_initial = y_train[initial_idx] |
| 49 | + |
| 50 | +# generate the pool |
| 51 | +# remove the initial data from the training dataset |
| 52 | +X_pool = np.delete(X_train, initial_idx, axis=0) |
| 53 | +y_pool = np.delete(y_train, initial_idx, axis=0) |
| 54 | + |
| 55 | +""" |
| 56 | +Query Strategy |
| 57 | +""" |
| 58 | + |
| 59 | +def max_entropy(learner, X, n_instances=1, T=100): |
| 60 | + subset = X[np.random.choice(range(len(X)), size=2000, replace=False)] |
| 61 | + MC_output = K.function([learner.estimator.model.layers[0].input, K.learning_phase()], |
| 62 | + [learner.estimator.model.layers[-1].output]) |
| 63 | + learning_phase = True |
| 64 | + MC_samples = [MC_output([subset, learning_phase])[0] for _ in range(T)] |
| 65 | + MC_samples = np.array(MC_samples) # [#samples x batch size x #classes] |
| 66 | + acquisition = - np.mean(np.sum(MC_samples * np.log(MC_samples + 1e-10), axis=-1), axis=0) # [batch size] |
| 67 | + query_idx = (-acquisition).argsort()[:n_instances] |
| 68 | + return query_idx, X[query_idx] |
| 69 | + |
| 70 | +def uniform(learner, X, n_instances=1): |
| 71 | + query_idx = np.random.choice(range(len(X)), size=n_instances, replace=False) |
| 72 | + return query_idx, X[query_idx] |
| 73 | + |
| 74 | +""" |
| 75 | +Training the ActiveLearner |
| 76 | +""" |
| 77 | + |
| 78 | +# initialize ActiveLearner |
| 79 | +learner = ActiveLearner( |
| 80 | + estimator=classifier, |
| 81 | + X_training=X_initial, |
| 82 | + y_training=y_initial, |
| 83 | + query_strategy=max_entropy, |
| 84 | + verbose=0 |
| 85 | +) |
| 86 | + |
| 87 | +# the active learning loop |
| 88 | +n_queries = 100 |
| 89 | +perf_hist = [learner.score(X_test, y_test, verbose=0)] |
| 90 | +for index in range(n_queries): |
| 91 | + query_idx, query_instance = learner.query(X_pool, n_instances=10) |
| 92 | + learner.teach(X_pool[query_idx], y_pool[query_idx], epochs=50, batch_size=128, verbose=0) |
| 93 | + # remove queried instance from pool |
| 94 | + X_pool = np.delete(X_pool, query_idx, axis=0) |
| 95 | + y_pool = np.delete(y_pool, query_idx, axis=0) |
| 96 | + model_accuracy = learner.score(X_test, y_test, verbose=0) |
| 97 | + print('Accuracy after query {n}: {acc:0.4f}'.format(n=index + 1, acc=model_accuracy)) |
| 98 | + perf_hist = [model_accuracy] |
| 99 | + |
| 100 | +np.save('/home/damien/Results/keras_modal_entropy.npy', perf_hist) |
| 101 | +print("saving to /home/damien/Results/keras_modal_entropy.npy") |
0 commit comments