package recunn.datasets;
import java.io.File;
import java.nio.charset.Charset;
import java.nio.file.Files;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.HashSet;
import java.util.List;
import java.util.Map;
import java.util.Random;
import java.util.Set;
import recunn.autodiff.Graph;
import recunn.datastructs.DataSequence;
import recunn.datastructs.DataSet;
import recunn.datastructs.DataStep;
import recunn.loss.LossSoftmax;
import recunn.matrix.Matrix;
import recunn.model.LinearUnit;
import recunn.model.Model;
import recunn.model.Nonlinearity;
import recunn.util.Util;
public class TextGenerationUnbroken extends DataSet {
private static final long serialVersionUID = 1L;
public static int reportSequenceLength = 100;
public static boolean reportPerplexity = true;
private static Map charToIndex = new HashMap<>();
private static Map indexToChar = new HashMap<>();
private static int dimension;
public static String generateText(Model model, int steps, boolean argmax, double temperature, Random rng) throws Exception {
Matrix start = new Matrix(dimension);
model.resetState();
Graph g = new Graph(false);
Matrix input = start.clone();
String result = "";
for (int s = 0; s < steps; s++) {
Matrix logprobs = model.forward(input, g);
Matrix probs = LossSoftmax.getSoftmaxProbs(logprobs, temperature);
int indxChosen = -1;
if (argmax) {
double high = Double.NEGATIVE_INFINITY;
for (int i = 0; i < probs.w.length; i++) {
if (probs.w[i] > high) {
high = probs.w[i];
indxChosen = i;
}
}
}
else {
indxChosen = Util.pickIndexFromRandomVector(probs, rng);
}
String ch = indexToChar.get(indxChosen);
result += ch;
for (int i = 0; i < input.w.length; i++) {
input.w[i] = 0;
}
input.w[indxChosen] = 1.0;
}
result = result.replace("\n", "\"\n\t\"");
return result;
}
public TextGenerationUnbroken(String path, int totalSequences, int sequenceMinLength, int sequenceMaxLength, Random rng) throws Exception {
System.out.println("Text generation task");
System.out.println("loading " + path + "...");
File file = new File(path);
List lines_ = Files.readAllLines(file.toPath(), Charset.defaultCharset());
String text = "";
for (String line : lines_) {
text += line + "\n";
}
Set chars = new HashSet<>();
int id = 0;
System.out.println("Characters:");
System.out.print("\t");
for (int i = 0; i < text.length(); i++) {
String ch = text.charAt(i) + "";
if (chars.contains(ch) == false) {
if (ch.equals("\n")) {
System.out.print("\\n");
}
else {
System.out.print(ch);
}
chars.add(ch);
charToIndex.put(ch, id);
indexToChar.put(id, ch);
id++;
}
}
System.out.println("");
dimension = chars.size();
List sequences = new ArrayList<>();
for (int s = 0; s < totalSequences; s++) {
List vecs = new ArrayList<>();
int len = rng.nextInt(sequenceMaxLength - sequenceMinLength + 1) + sequenceMinLength;
int start = rng.nextInt(text.length() - len);
for (int i = 0; i < len; i++) {
String ch = text.charAt(i+start) + "";
int index = charToIndex.get(ch);
double[] vec = new double[dimension];
vec[index] = 1.0;
vecs.add(vec);
}
DataSequence sequence = new DataSequence();
for (int i = 0; i < vecs.size() - 1; i++) {
sequence.steps.add(new DataStep(vecs.get(i), vecs.get(i+1)));
}
sequences.add(sequence);
}
System.out.println("Total unique chars = " + chars.size());
training = sequences;
lossTraining = new LossSoftmax();
lossReporting = new LossSoftmax();
inputDimension = sequences.get(0).steps.get(0).input.w.length;
int loc = 0;
while (sequences.get(0).steps.get(loc).targetOutput == null) {
loc++;
}
outputDimension = sequences.get(0).steps.get(loc).targetOutput.w.length;
}
@Override
public void DisplayReport(Model model, Random rng) throws Exception {
System.out.println("========================================");
System.out.println("REPORT:");
if (reportPerplexity) {
System.out.println("\ncalculating perplexity over entire data set...");
double perplexity = LossSoftmax.calculateMedianPerplexity(model, training);
System.out.println("\nMedian Perplexity = " + String.format("%.4f", perplexity));
}
double[] temperatures = {1, 0.75, 0.5, 0.25, 0.1};
for (double temperature : temperatures) {
System.out.println("\nTemperature "+temperature+" prediction:");
String guess = TextGenerationUnbroken.generateText(model, reportSequenceLength, false, temperature, rng);
System.out.println("\t\"..." + guess + "...\"");
}
System.out.println("\nArgmax prediction:");
String guess = TextGenerationUnbroken.generateText(model, reportSequenceLength, true, 1.0, rng);
System.out.println("\t\"..." + guess + "...\"");
System.out.println("========================================");
}
@Override
public Nonlinearity getModelOutputUnitToUse() {
return new LinearUnit();
}
}
Ads help maintain this website.