class Predictor(): def __init__(self): try: f = open("params.json", "r", encoding='utf8') self.params = json.loads(f.read()) except FileNotFoundError: self.params = save_corpus() device = torch.device('cuda' if torch.cuda.is_available() else 'cpu') self.device = device self.model = BiGRU(torch.zeros((len(self.params['tbl']) + 1, 300)), MODEL_PARAMS['gru_hidden_dim'], MODEL_PARAMS['gru_num_layers'], len(self.params['tagset']), MODEL_PARAMS['concat']).to(device) self.model.load_state_dict( torch.load('trained_model.pt', map_location=lambda storage, loc: storage)) self.model.eval() def predict(self, sentence): words = sentence.split() lis = [] new_words = [] for word in words: symbol = None if not word[-1].isalnum(): symbol = word[-1] word = word[:-1] if word.lower() in self.params['tbl']: lis.append(self.params['tbl'][word.lower()]) else: lis.append(0) new_words.append(word) if symbol != None: if symbol in self.params['tbl']: lis.append(self.params['tbl'][symbol]) else: lis.append(0) new_words.append(symbol) x = torch.LongTensor(lis).to(self.device) x = x.unsqueeze(0) y_raw = self.model(x) y_pred = torch.argmax(y_raw, dim=2).view(-1) tagged_sent = '' for i in range(len(y_pred)): tagged_sent += new_words[i] tagged_sent += ' ' tagged_sent += self.params['reverse_tagset'][y_pred[i]] tagged_sent += ' ' print(tagged_sent) def tag_lookup(self, tag): try: print('TAG:', tag) print('Definition:', self.params['tag_definition'][tag][0]) except: print('Error: Tag not found.')
def main(options): use_cuda = (len(options.gpuid) >= 1) if options.gpuid: cuda.set_device(options.gpuid[0]) train, dev, test, vocab = torch.load(open(options.data_file, 'rb'), pickle_module=dill) batched_train, batched_train_mask, _ = utils.tensor.advanced_batchize( train, options.batch_size, vocab.stoi["<pad>"]) batched_dev, batched_dev_mask, _ = utils.tensor.advanced_batchize( dev, options.batch_size, vocab.stoi["<pad>"]) vocab_size = len(vocab) rnnlm = BiGRU(vocab_size, use_cuda=use_cuda) if use_cuda > 0: rnnlm.cuda() else: rnnlm.cpu() criterion = torch.nn.NLLLoss() optimizer = eval("torch.optim." + options.optimizer)(rnnlm.parameters(), options.learning_rate) # main training loop last_dev_avg_loss = float("inf") rnnlm.train() for epoch_i in range(options.epochs): logging.info("At {0}-th epoch.".format(epoch_i)) # srange generates a lazy sequence of shuffled range for i, batch_i in enumerate(utils.rand.srange(len(batched_train))): train_batch = Variable( batched_train[batch_i]) # of size (seq_len, batch_size) train_mask = Variable(batched_train_mask[batch_i]) train_in_mask = train_mask.view(-1) train_out_mask = train_mask.view(-1) if use_cuda: train_batch = train_batch.cuda() train_mask = train_mask.cuda() train_in_mask = train_in_mask.cuda() train_out_mask = train_out_mask.cuda() sys_out_batch = rnnlm( train_batch ) # (seq_len, batch_size, vocab_size) # TODO: substitute this with your module train_in_mask = train_in_mask.unsqueeze(1).expand( len(train_in_mask), vocab_size) sys_out_batch = sys_out_batch.view(-1, vocab_size) train_out_batch = train_batch.view(-1) sys_out_batch = sys_out_batch.masked_select(train_in_mask).view( -1, vocab_size) train_out_batch = train_out_batch.masked_select(train_out_mask) loss = criterion(sys_out_batch, train_out_batch) logging.debug("loss at batch {0}: {1}".format(i, loss.data[0])) optimizer.zero_grad() loss.backward() optimizer.step() # validation -- this is a crude esitmation because there might be some paddings at the end dev_loss = 0.0 rnnlm.eval() for batch_i in range(len(batched_dev)): dev_batch = Variable(batched_dev[batch_i], volatile=True) dev_mask = Variable(batched_dev_mask[batch_i], volatile=True) dev_in_mask = dev_mask.view(-1) dev_out_batch = dev_batch.view(-1) if use_cuda: dev_batch = dev_batch.cuda() dev_mask = dev_mask.cuda() dev_in_mask = dev_in_mask.cuda() dev_out_batch = dev_out_batch.cuda() sys_out_batch = rnnlm(dev_batch) dev_in_mask = dev_in_mask.unsqueeze(1).expand( len(dev_in_mask), vocab_size) dev_out_mask = dev_mask.view(-1) sys_out_batch = sys_out_batch.view(-1, vocab_size) sys_out_batch = sys_out_batch.masked_select(dev_in_mask).view( -1, vocab_size) dev_out_batch = dev_out_batch.masked_select(dev_out_mask) loss = criterion(sys_out_batch, dev_out_batch) dev_loss += loss dev_avg_loss = dev_loss / len(batched_dev) logging.info( "Average loss value per instance is {0} at the end of epoch {1}". format(dev_avg_loss.data[0], epoch_i)) if (last_dev_avg_loss - dev_avg_loss).data[0] < options.estop: logging.info( "Early stopping triggered with threshold {0} (previous dev loss: {1}, current: {2})" .format(epoch_i, last_dev_avg_loss.data[0], dev_avg_loss.data[0])) break torch.save( rnnlm, open( options.model_file + ".nll_{0:.2f}.epoch_{1}".format(dev_avg_loss.data[0], epoch_i), 'wb'), pickle_module=dill) last_dev_avg_loss = dev_avg_loss