Active learning reduces the number of labels needed for supervised learning by letting the learner choose which examples to label. It is useful when unlabeled data is abundant but obtaining labels is expensive. An unlabeled instance becomes a query to an oracle, which supplies its label. The aim is high predictive accuracy with as few labeled instances as possible. section 7.3
In pool-based active learning, start with a small labeled set L and a larger unlabeled pool U. Score candidates in U for informativeness, select queries, and add their oracle-supplied labels to L. Ranking the entire pool can be costly for very large datasets; stream-based sampling instead scans instances sequentially and makes an individual query decision for each. section 7.3
Two query strategies differ in what they regard as informative:
- Uncertainty sampling selects predictions the current model is least sure about. For binary logistic regression, these lie near the decision boundary, where the predicted positive-class probability approaches ½. Multiclass criteria include lowest confidence in the top class, the smallest margin between the top two classes, and highest predictive entropy. For regression, query the point with the highest predicted output variance. section 7.3.1
- Query by committee trains competing models on the current labeled set. Each model votes on candidate labels; disagreement identifies informative queries. Vote entropy and average KL divergence are supported committee-ranking strategies. section 7.3.1
Thirty labels for logistic regression
On a synthetic, balanced binary-classification dataset, logistic regression trained on 30 randomly selected labels reaches 90% accuracy on held-out data. With 30 queries chosen by entropy-based uncertainty sampling, it reaches 92.5%. Compare both decision boundaries and held-out scores rather than assuming every query strategy will improve accuracy. section 7.3 section 7.3.1
Listing 7.5 Active learner class
from __future__ import unicode_literals, division
from scipy.sparse import csc_matrix, vstack
from scipy.stats import entropy
from collections import Counter
import numpy as np
class ActiveLearner(object):
uncertainty_sampling_frameworks = [
'entropy', #1
'max_margin', #1
'least_confident', #1
]
query_by_committee_frameworks = [
'vote_entropy',
'average_kl_divergence', #2
] #2
def __init__(self, strategy='least_confident'):
self.strategy = strategy
def rank(self, clf, X_unlabeled, num_queries=None):
if num_queries == None:
num_queries = X_unlabeled.shape[0]
elif type(num_queries) == float:
num_queries = int(num_queries * X_unlabeled.shape[0])
if self.strategy in self.uncertainty_sampling_frameworks:
scores = self.uncertainty_sampling(clf, X_unlabeled)
elif self.strategy in self.query_by_committee_frameworks:
scores = self.query_by_committee(clf, X_unlabeled)
else:
raise ValueError("this strategy is not implemented.")
rankings = np.argsort(-scores)[:num_queries]
return rankings
def uncertainty_sampling(self, clf, X_unlabeled):
probs = clf.predict_proba(X_unlabeled)
if self.strategy == 'least_confident':
return 1 - np.amax(probs, axis=1) #3
elif self.strategy == 'max_margin':
margin = np.partition(-probs, 1, axis=1)
return -np.abs(margin[:,0] - margin[:, 1]) #4
elif self.strategy == 'entropy':
return np.apply_along_axis(entropy, 1,
probs) #5
def query_by_committee(self, clf, X_unlabeled):
num_classes = len(clf[0].classes_)
C = len(clf)
preds = []
if self.strategy == 'vote_entropy':
for model in clf:
y_out = map(int, model.predict(X_unlabeled))
preds.append(np.eye(num_classes)[y_out])
votes = np.apply_along_axis(np.sum, 0, np.stack(preds)) / C
return np.apply_along_axis(entropy, 1,
votes) #6
elif self.strategy == 'average_kl_divergence':
for model in clf:
preds.append(model.predict_proba(X_unlabeled))
consensus = np.mean(np.stack(preds), axis=0)
divergence = []
for y_out in preds:
divergence.append(entropy(consensus.T, y_out.T))
return np.apply_along_axis(np.mean, 0, np
.stack(divergence)) #7
The ActiveLearner class shows how to implement candidate ranking with selectable uncertainty-sampling and query-by-committee criteria. section 7.3.1


