We can pass the vectorized training data (using the method we defined in the previous section) to our chatbot and call the memory network's fit method to train over mini-batches of the training data while evaluating our model's performance on the validation set at fixed intervals:
def predict_for_batch(self, facts, questions):
preds = []
# Iterate over mini-batches
for start in range(0, len(facts), self.batch_size):
end = start + self.batch_size
facts_batch = facts[start:end]
questions_batch = questions[start:end]
# Predict per batch
pred = self.model.predict(facts_batch, questions_batch)
preds += list(pred)
return preds
def train(self):
# Vectorize training and validation data
train_facts, train_questions, train_answers = vectorize_data(
self.train_data, self.word_idx, self.sentence_size,
self.batch_size, self.memory_size)
val_facts, val_questions, val_answers = vectorize_data(
self.val_data, self.word_idx, self.sentence_size,
self.batch_size, self.memory_size)
# Chunk training data into batches
batches = zip(range(0, len(train_facts) - self.batch_size,
self.batch_size),
range(self.batch_size, len(train_facts),
self.batch_size))
batches = [(start, end) for start, end in batches]
# Start training loop
for epoch in range(1, self.epochs + 1):
np.random.shuffle(batches)
total_cost = 0.0
for start, end in batches:
facts = train_facts[start:end]
questions = train_questions[start:end]
answers = train_answers[start:end]
# Train on batch
batch_cost = self.model.fit(facts, questions, answers)
total_cost += batch_cost
if epoch % self.evaluation_interval == 0:
# Compute accuracy over training and validation set
train_preds = self.predict_for_batch(
train_facts, train_questions)
val_preds = self.predict_for_batch(
val_facts, val_questions)
train_acc = metrics.accuracy_score(
train_preds, train_answers)
val_acc = metrics.accuracy_score(
val_preds, val_answers)
print("Epoch: ", epoch)
print("Total Cost: ", total_cost)
print("Training Accuracy: ", train_acc)
print("Validation Accuracy: ", val_acc)
print("---")