<commit_before>package org.javarosa.core.util;

import java.util.Enumeration;
import java.util.Hashtable;
import java.util.Stack;
import java.util.Vector;

/**
 * Directed A-cyclic (NOT ENFORCED) graph datatype.
 *
 * Genericized with three types: An unique index value (representing the node), a generic
 * set of data to associate with that node, and a piece of data to associate with each
 * edge
 *
 * @author ctsims
 */
public class DAG<I, N, E> {
    //TODO: This is a really unsafe datatype. Needs an absurd amount of updating for representation
    //invariance, synchronicity, cycle detection, etc.

    private final Hashtable<I, N> nodes;
    private final Hashtable<I, Vector<Edge<I, E>>> edge;
    private final Hashtable<I, Vector<Edge<I, E>>> inverse;

    public DAG() {
        nodes = new Hashtable<I, N>();
        edge = new Hashtable<I, Vector<Edge<I, E>>>();
        inverse = new Hashtable<I, Vector<Edge<I, E>>>();
    }

    public void addNode(I i, N n) {
        nodes.put(i, n);
    }

    /**
     * Connect Source -> Destination
     */
    public void setEdge(I source, I destination, E edgeData) {
        addToEdge(edge, source, destination, edgeData);
        addToEdge(inverse, destination, source, edgeData);
    }

    private void addToEdge(Hashtable<I, Vector<Edge<I, E>>> edgeList, I a, I b, E edgeData) {
        Vector<Edge<I, E>> edge;
        if (edgeList.containsKey(a)) {
            edge = edgeList.get(a);
        } else {
            edge = new Vector<Edge<I, E>>();
        }
        edge.addElement(new Edge<I, E>(b, edgeData));
        edgeList.put(a, edge);
    }

    public Vector<Edge<I, E>> getParents(I index) {
        if (inverse.containsKey(index)) {
            return inverse.get(index);
        } else {
            return new Vector<Edge<I, E>>();
        }
    }

    public Vector<Edge<I, E>> getChildren(I index) {
        if (!edge.containsKey(index)) {
            return new Vector<Edge<I, E>>();
        } else {
            return edge.get(index);
        }
    }

    public N getNode(I index) {
        return nodes.get(index);
    }

    /**
     * @return Indices for all nodes in the graph which are not the target of
     * any edges in the graph
     */
    public Stack<I> getSources() {
        Stack<I> sources = new Stack<I>();
        for (Enumeration en = nodes.keys(); en.hasMoreElements(); ) {
            I i = (I)en.nextElement();
            if (!inverse.containsKey(i)) {
                sources.addElement(i);
            }
        }
        return sources;
    }

    /**
     * @return Indices for all nodes that do not have any outgoing edges
     */
    public Stack<I> getSinks() {
        Stack<I> roots = new Stack<I>();
        for (Enumeration en = nodes.keys(); en.hasMoreElements(); ) {
            I i = (I)en.nextElement();
            if (!edge.containsKey(i)) {
                roots.addElement(i);
            }
        }
        return roots;
    }

    public static class Edge<I, E> {
        public final I i;
        public final E e;

        public Edge(I i, E e) {
            this.i = i;
            this.e = e;
        }
    }

    public Enumeration getNodes() {
        return nodes.elements();
    }

    public Enumeration getIndices() {
        return nodes.keys();
    }
}<commit_msg>changes to DAG class to support being able to remove missing cases from case DAG<commit_after>package org.javarosa.core.util;

import java.util.Enumeration;
import java.util.Hashtable;
import java.util.Stack;
import java.util.Vector;

/**
 * Directed A-cyclic (NOT ENFORCED) graph datatype.
 *
 * Genericized with three types: An unique index value (representing the node), a generic
 * set of data to associate with that node, and a piece of data to associate with each
 * edge
 *
 * @author ctsims
 */
public class DAG<I, N, E> {
    //TODO: This is a really unsafe datatype. Needs an absurd amount of updating for representation
    //invariance, synchronicity, cycle detection, etc.

    private final Hashtable<I, N> nodes;
    private final Hashtable<I, Vector<Edge<I, E>>> edges;
    private final Hashtable<I, Vector<Edge<I, E>>> inverseEdges;

    public DAG() {
        nodes = new Hashtable<I, N>();
        edges = new Hashtable<I, Vector<Edge<I, E>>>();
        inverseEdges = new Hashtable<I, Vector<Edge<I, E>>>();
    }

    public void addNode(I i, N n) {
        nodes.put(i, n);
    }

    public void removeNode(I i) {
        nodes.remove(i);
    }

    /**
     * Connect Source -> Destination
     */
    public void setEdge(I source, I destination, E edgeData) {
        addToEdges(edges, source, destination, edgeData);
        addToEdges(inverseEdges, destination, source, edgeData);
    }

    private void addToEdges(Hashtable<I, Vector<Edge<I, E>>> edgeList, I source, I dest, E edgeData) {
        Vector<Edge<I, E>> edge;
        if (edgeList.containsKey(source)) {
            edge = edgeList.get(source);
        } else {
            edge = new Vector<Edge<I, E>>();
        }
        edge.addElement(new Edge<I, E>(dest, edgeData));
        edgeList.put(source, edge);
    }

    /**
     * If an edge exists in the graph from sourceIndex to destinationIndex, remove it
     */
    public void removeEdge(I sourceIndex, I destinationIndex) {
        Vector<Edge<I, E>> edgesFromSource = edges.get(sourceIndex);
        for (Edge<I, E> edge : edgesFromSource) {
            if (edge.i.equals(destinationIndex)) {
                edgesFromSource.remove(edge);
                return;
            }
        }
    }

    public Vector<Edge<I, E>> getParents(I index) {
        if (inverseEdges.containsKey(index)) {
            return inverseEdges.get(index);
        } else {
            return new Vector<Edge<I, E>>();
        }
    }

    public Vector<Edge<I, E>> getChildren(I index) {
        if (!edges.containsKey(index)) {
            return new Vector<Edge<I, E>>();
        } else {
            return edges.get(index);
        }
    }

    public N getNode(I index) {
        return nodes.get(index);
    }

    /**
     * @return Indices for all nodes in the graph which are not the target of
     * any edges in the graph
     */
    public Stack<I> getSources() {
        Stack<I> sources = new Stack<I>();
        for (Enumeration en = nodes.keys(); en.hasMoreElements(); ) {
            I i = (I)en.nextElement();
            if (!inverseEdges.containsKey(i)) {
                sources.addElement(i);
            }
        }
        return sources;
    }

    /**
     * @return Indices for all nodes that do not have any outgoing edges
     */
    public Stack<I> getSinks() {
        Stack<I> roots = new Stack<I>();
        for (Enumeration en = nodes.keys(); en.hasMoreElements(); ) {
            I i = (I)en.nextElement();
            if (!edges.containsKey(i)) {
                roots.addElement(i);
            }
        }
        return roots;
    }

    public static class Edge<I, E> {
        public final I i;
        public final E e;

        public Edge(I i, E e) {
            this.i = i;
            this.e = e;
        }
    }

    public Enumeration getNodes() {
        return nodes.elements();
    }

    public Enumeration getIndices() {
        return nodes.keys();
    }
}
{'fraction_non_alphanumeric': 0.12312146697918103, 'fraction_numerical': 0.0, 'mean_word_length': 2.068527918781726, 'pattern_counts': {'":': 0, '<': 82, '<?xml version=': 0, '>': 84, 'https://': 0, 'lorem ipsum': 0, 'www.': 0, 'xml': 0}, 'pii_count': 0, 'substrings_counts': 0, 'word_list_counts': {'cursed_substrings.json': 0, 'profanity_word_list.json': 0, 'sexual_word_list.json': 0, 'zh_pornsignals.json': 0}}
{'dir': 'git-commits-cleaned', 'id': '4620755', 'n_tokens_mistral': 2240, 'n_tokens_neox': 2194, 'n_words': 653}