List <Graph> readDataset(string _sFile) { List <Graph> D = new List <Graph>(); string line = ""; using (StreamReader sr = File.OpenText(_sFile)) { Graph G = null; while ((line = sr.ReadLine()) != null) { if (line.Contains("t")) // graph { G = new Graph(); G.nodes = new List <Node>(); G.edges = new List <DFS_Code>(); // add graph to dataset D.Add(G); G.id = int.Parse(line.Split()[2]); } else if (line.Contains("v")) // vertex { if (G != null) { Node node = new Node(); node.id = int.Parse(line.Split()[1]); node.label = int.Parse(line.Split()[2]); G.nodes.Add(node); } } else if (line.Contains("e")) // edge { if (G != null) { DFS_Code code = new DFS_Code(); code.u = int.Parse(line.Split()[1]); code.v = int.Parse(line.Split()[2]); code.l_u = G.nodes[code.u].label; code.l_v = G.nodes[code.v].label; code.l_w = int.Parse(line.Split()[3]); code.support = 1; code.GraphID = G.id; G.edges.Add(code); } } } } return(D); }
bool IsCanonical(List <DFS_Code> C, int support) { Graph GC = new Graph(); // graph corresponding to code C GC.id = -1; GC.support = support; GC.nodes = new List <Node>(); GC.edges = new List <DFS_Code>(C); foreach (DFS_Code code in C) { Node node_u = new Node() { id = code.u, label = code.l_u }; if (!GC.nodes.Contains(node_u)) { GC.nodes.Add(node_u); } Node node_v = new Node() { id = code.v, label = code.l_v }; if (!GC.nodes.Contains(node_v)) { GC.nodes.Add(node_v); } } List <Graph> DC = new List <Graph>(); DC.Add(GC); List <DFS_Code> C1 = new List <DFS_Code>(); // initialize canonical DFS code foreach (DFS_Code t in C) { List <DFS_Code> extensions = RightMostPath_Extensions(C1, DC); // extensions of C1 // get least righmost edge extension of C1 DFS_Code s = extensions[0]; if (s.LessThan(t)) { return(false); // C1 is smaller, thus C is not canonical } C1.Add(s); } //result.Add(GC); // NEW return(true); // no smaller code exists; C is canonical }
List <DFS_Code> RightMostPath_Extensions(List <DFS_Code> C, List <Graph> D) { List <Node> R = null; Node ur = null; if (C.Count > 0) { // find nodes on the rightmost path in C R = getNodesOnRightMostPath(C); // get DFS Code of the rightmost child in C ur = R[0]; } List <DFS_Code> extensions = new List <DFS_Code>(); foreach (Graph G in D) { if (C.Count == 0) // root node { // add distinct label tuples in G as forward extensions foreach (DFS_Code dfs in G.edges) { DFS_Code f = new DFS_Code() { u = 0, v = 1, l_u = dfs.l_u, l_v = dfs.l_v, l_w = dfs.l_w, support = 1, GraphID = G.id }; if (!extensions.Contains(f)) // extensions do not contain f yet! { extensions.Add(f); } // NEW CODE f = new DFS_Code() { u = 0, v = 1, l_u = dfs.l_v, l_v = dfs.l_u, l_w = dfs.l_w, support = 1, GraphID = G.id }; if (!extensions.Contains(f)) // extensions do not contain f yet! { extensions.Add(f); } } } else { List <Isomorphism> iso = SubGraphIsomorphisms(C, G); foreach (Isomorphism o in iso) { // backward extensions from the rightmost child Node node_ur = new Node() { id = o.map[ur.id], label = ur.label }; // node ur in G foreach (Neighbor x in getNeighbors(node_ur, G)) { Node node_v = new Node(); // node v is a mapping of node x in C //node_v.id = o.map.FirstOrDefault(a => a.Value == x.id).Key; node_v.id = -1; foreach (var kv in o.map) { if (kv.Value == x.id) { node_v.id = kv.Key; break; } } node_v.label = x.label; if (node_v.id != -1) // node v is existing in C { // rightmost path contains node v && edge (ur, v) is new in C if (R.Contains(node_v) && !checkEdge(ur.id, node_v.id, C)) { DFS_Code f = new DFS_Code() { u = ur.id, v = node_v.id, l_u = ur.label, l_v = node_v.label, l_w = x.edge, support = 1, GraphID = G.id }; if (!extensions.Contains(f)) // do not add duplicate tupes { extensions.Add(f); } } } } // forward extensions from nodes on rightmost path foreach (Node u in R) { Node node_u = new Node() { id = o.map[u.id], label = u.label }; // node u in G foreach (Neighbor x in getNeighbors(node_u, G)) { // node v is a mapping of node x in C //int v = o.map.FirstOrDefault(a => a.Value == x.id).Key; int v = -1; foreach (var kv in o.map) { if (kv.Value == x.id) { v = kv.Key; break; } } if (v == -1) { DFS_Code f = new DFS_Code() { u = u.id, v = ur.id + 1, l_u = node_u.label, l_v = x.label, l_w = x.edge, support = 1, GraphID = G.id }; if (!extensions.Contains(f)) // do not add duplicate tupes { extensions.Add(f); } } } } } } } // in extensions, there are no duplicate tupes in the same graph // compute the support of each extension for (int i = 0; i < extensions.Count() - 1; i++) { DFS_Code s = extensions[i]; for (int j = i + 1; j < extensions.Count(); j++) { DFS_Code t = extensions[j]; if (s.u == t.u && s.v == t.v && s.l_u == t.l_u && s.l_v == t.l_v && s.l_w == t.l_w) { s.support += 1; extensions.RemoveAt(j); j--; } } } // sort extensions for (int i = 0; i < extensions.Count() - 1; i++) { for (int j = i + 1; j < extensions.Count(); j++) { if (extensions[j].LessThan(extensions[i])) { DFS_Code code = extensions[i]; extensions[i] = extensions[j]; extensions[j] = code; } } } return(extensions); }