/* * Adds nodes to graph */ private static void addNodes() { String current; Node node; Node fromNode; try { line = br.readLine(); while (line.indexOf(",") != -1) { current = line.substring(0, line.indexOf(",")); current = current.trim(); line = line.substring(line.indexOf(",") + 1); if (nodeMap.get(current.charAt(1)) == null) { node = new Node(current.charAt(1)); nodeMap.put(current.charAt(1), node); } if (nodeMap.get(current.charAt(0)) == null) { node = new Node(current.charAt(1)); nodeMap.put(current.charAt(0), node); } fromNode = nodeMap.get(current.charAt(0)); fromNode.addEdge(nodeMap.get(current.charAt(1)), current.charAt(2) - '0'); } } catch (IOException e) { System.out.println(e); } }
/** * Perform the reduce phase. * * <p>Input (edge,value) - Input key is a compressed representation of the K-mer representing an * edge. The value is a tab delimeted field providing information about the edge and the two k-1 * mers it connects. For more info see the javadoc for the mappers. * * <p>Output (kmer,node) key - The key is a compressed version of the K-Mer representing a * source Node. node - A serialized version of a Node object representing the source node. This * object contains all of the outgoing edges for this node. */ public void reduce( Text curnode, Iterator<Text> iter, OutputCollector<Text, Text> output, Reporter reporter) throws IOException { Node node = new Node(); String mertag = null; float cov = 0; // The keys for edges map are the two characte type code, // e.g "ff", "rf", "rr","fr" assigned to each edge based // on the canonical direction of the read. // // The values are a MAP contain the neighbors for this read. // The keys of the negbors are the DNA character e.g "A" representing // the base we need to add to the K-Mer representing this node so that // we can construct the two k Mers connected by the k-1 Mer of overlap // where the outgoing node is represented by currnode Map<String, Map<String, List<String>>> edges = new HashMap<String, Map<String, List<String>>>(); // loop over all the tuples for this kmer. Since they keys, are the same. // The k-1 Mer representing the starting node and the K-mer representing the edge are the // same. while (iter.hasNext()) { String valstr = iter.next().toString(); String[] vals = valstr.split("\t"); String type = vals[0]; // edge type between mers String neighbor = vals[1]; // id of neighboring node String tag = vals[2]; // id of read contributing to edge String state = vals[3]; // internal or end mer // Add the edge to the neighbor Map<String, List<String>> neighborinfo = null; if (edges.containsKey(type)) { neighborinfo = edges.get(type); } else { neighborinfo = new HashMap<String, List<String>>(); edges.put(type, neighborinfo); } // Now record the read supports the edge List<String> tags = null; if (neighborinfo.containsKey(neighbor)) { tags = neighborinfo.get(neighbor); } else { tags = new ArrayList<String>(); neighborinfo.put(neighbor, tags); } if (tags.size() < MAXTHREADREADS) { tags.add(tag); } // Check on the mertag // set mertag to the smallest (lexicographically) tag // of all the tags associated with this key if (mertag == null || (tag.compareTo(mertag) < 0)) { mertag = tag; } // Update coverage, offsets if (!state.equals("i")) { cov++; if (state.equals("6")) { node.addR5(tag, K - 1, 1, MAXR5); } else if (state.equals("5")) { node.addR5(tag, 0, 0, MAXR5); } } } node.setMertag(mertag); node.setCoverage(cov); // Decode the key for the input tuple into a DNA sequence. String seq = Node.dna2str(curnode.toString()); String rc = Node.rc(seq); // create a node representing the k-mer corresponding // to the key node.setstr_raw(curnode.toString()); // extract the k-1 Mers corresponding the overlap // between the KMers seq = seq.substring(1); rc = rc.substring(1); char[] dirs = {'f', 'r'}; for (int d = 0; d < 2; d++) { String x = Character.toString(dirs[d]); int degree = 0; for (int e = 0; e < 2; e++) { String t = x + dirs[e]; if (edges.containsKey(t)) { degree += edges.get(t).size(); } } for (int e = 0; e < 2; e++) { String t = x + dirs[e]; if (edges.containsKey(t)) { Map<String, List<String>> edgeinfo = edges.get(t); for (String vc : edgeinfo.keySet()) { String v = seq; if (dirs[d] == 'r') { v = rc; } // Construct the k-Mer corresponding to the destination // node for this edge. seq is the K-1 Mer of overlap. // vc (the keys of edgeinfo) are the base we need to add // to the k-1 overlap to get the destination kmer v = v + vc; if (dirs[e] == 'r') { v = Node.rc(v); } String link = Node.str2dna(v); node.addEdge(t, link); if ((degree > 1) || RECORD_ALL_THREADS) { for (String r : edgeinfo.get(vc)) { node.addThread(t, link, r); } } } } } } output.collect(curnode, new Text(node.toNodeMsg())); reporter.incrCounter("Contrail", "nodecount", 1); }
public static void main(String[] args) { Node seven = new Node("7"); Node five = new Node("5"); Node three = new Node("3"); Node eleven = new Node("11"); Node eight = new Node("8"); Node two = new Node("2"); Node nine = new Node("9"); Node ten = new Node("10"); seven.addEdge(eleven).addEdge(eight); three.addEdge(eight).addEdge(ten); five.addEdge(eleven); eleven.addEdge(two).addEdge(nine).addEdge(ten); eight.addEdge(nine).addEdge(ten); Node[] allNodes = {seven, five, three, eleven, eight, two, ten, nine}; // L <- Empty list that will contain the sorted elements ArrayList<Node> L = new ArrayList<Node>(); // S <- Set of all nodes with no incoming edges HashSet<Node> S = new HashSet<Node>(); for (Node n : allNodes) { if (n.inEdges.size() == 0) { S.add(n); } } // while S is non-empty do while (!S.isEmpty()) { // remove a node n from S Node n = S.iterator().next(); S.remove(n); // insert n into L L.add(n); // for each node m with an edge e from n to m do for (Iterator<Edge> it = n.outEdges.iterator(); it.hasNext(); ) { // remove edge e from the graph Edge e = it.next(); Node m = e.to; it.remove(); // Remove edge from n m.inEdges.remove(e); // Remove edge from m // if m has no other incoming edges then insert m into S if (m.inEdges.isEmpty()) { S.add(m); } } } // Check to see if all edges are removed boolean cycle = false; for (Node n : allNodes) { if (!n.inEdges.isEmpty()) { cycle = true; break; } } if (cycle) { System.out.println("Cycle present, topological sort not possible"); } else { System.out.println("Topological Sort: " + Arrays.toString(L.toArray())); } }