def checkRings(cycles): """This fixes a bug in figuras algorithm. Sometimes when traversing through fused rings embedded in a larger ring two paths are returned when only one should have been This removes (most) of these cases""" # XXX I've encountered this bug before in figueras algorithm # I really need to investigate if further and see # if CDK has the same issues. res = [] set = kjSet() sameSizes = {} i = 0 for atoms, bonds in cycles: size = len(bonds) sameSizes[size] = sameSizes.get(size, []) + [(atoms, bonds)] keys = sameSizes.keys() keys.sort() last = kjSet() for size in keys: cycles = sameSizes[size] nextCycles = kjSet() i = 0 if len(cycles) == 1: res.append(cycles[0]) print "adding ring of size", cycles[0][1] continue dontAdd = {} for atoms1, bonds1 in cycles: s1 = kjSet(bonds1) j = i + 1 for atom2, bonds2 in cycles[j:]: s2 = kjSet(bonds2) check = (s1-s2) + (s2-s1) l = len(check) if not (l and len(last & check) == l): print "adding ring of size", len(bonds1) res.append((atoms1, bonds1)) else: if i not in dontAdd: dontAdd[j] = 1 res.append((atoms1, bonds1)) print "adding ring of size", len(bonds1) print "dropping ring of size", len(bonds2) i += 1 nextCycles += s1 last += nextCycles return res
def checkRings(cycles): """This fixes a bug in figuras algorithm. Sometimes when traversing through fused rings embedded in a larger ring two paths are returned when only one should have been This removes (most) of these cases""" # XXX I've encountered this bug before in figueras algorithm # I really need to investigate if further and see # if CDK has the same issues. res = [] set = kjSet() sameSizes = {} i = 0 for atoms, bonds in cycles: size = len(bonds) sameSizes[size] = sameSizes.get(size, []) + [(atoms, bonds)] keys = sameSizes.keys() keys.sort() last = kjSet() for size in keys: cycles = sameSizes[size] nextCycles = kjSet() i = 0 if len(cycles) == 1: res.append(cycles[0]) print "adding ring of size", cycles[0][1] continue dontAdd = {} for atoms1, bonds1 in cycles: s1 = kjSet(bonds1) j = i + 1 for atom2, bonds2 in cycles[j:]: s2 = kjSet(bonds2) check = (s1 - s2) + (s2 - s1) l = len(check) if not (l and len(last & check) == l): print "adding ring of size", len(bonds1) res.append((atoms1, bonds1)) else: if i not in dontAdd: dontAdd[j] = 1 res.append((atoms1, bonds1)) print "adding ring of size", len(bonds1) print "dropping ring of size", len(bonds2) i += 1 nextCycles += s1 last += nextCycles return res
def factor(G): from kjbuckets import kjSet, kjGraph allnodes = kjSet(G.keys()) + kjSet(G.values()) allnodelist = allnodes.items() allnodemap = map(None, allnodelist, range(len(allnodelist))) nodetoindex = kjGraph(allnodemap) pairs = G.items() left = pairs[:] right = left[:] for i in xrange(len(left)): (l, r) = pairs[i] left[i], right[i] = nodetoindex[l], nodetoindex[r] return (left, right), allnodelist
def tsort(list_of_pairs): result = [] Graph = kjGraph(list_of_pairs) notsource = (kjSet(Graph.values()) - kjSet(Graph.keys())).items() while Graph: sources = kjSet(Graph.keys()) dests = kjSet(Graph.values()) startingpoints = sources - dests if not startingpoints: raise LOOPERROR, "loop detected in Graph" for node in startingpoints.items(): result.append(node) del Graph[node] return result + notsource
def tsort(pairs): from kjbuckets import kjGraph, kjSet G = kjGraph(pairs) Gt = ~G # transpose sources = kjSet(G.keys()) dests = kjSet(G.values()) all = (sources + dests).items() total = len(all) endpoints = dests - sources for i in xrange(total - 1, -1, -1): #print i, endpoints if not endpoints: raise LOOPERROR, "loop detected" choice = endpoints.choose_key() for n in Gt.neighbors(choice): G.delete_arc(n, choice) if not G.has_key(n): endpoints[n] = n del endpoints[choice] all[i] = choice return all
def calc_mincut( me, g, uncutables =(), exclude_selfrefs =True, count_multiples =True): edge_cost = me.edge_cost = {} for edge in g: if edge in uncutables: cost = len(g) else: cost = count_multiples and g.count(edge) or 1 edge_cost[ edge] = cost g = kj.kjGraph( g) #prngraph( g & ~g.tclosure() ) #- core-cycle if exclude_selfrefs: # self_refs = kj.kjSet(g).ident() & g # g = g - self_refs g = g - kj.kjSet(g).ident() me._find( g)
def calc_mincut(me, g, uncutables=(), exclude_selfrefs=True, count_multiples=True): edge_cost = me.edge_cost = {} for edge in g: if edge in uncutables: cost = len(g) else: cost = count_multiples and g.count(edge) or 1 edge_cost[edge] = cost g = kj.kjGraph(g) #prngraph( g & ~g.tclosure() ) #- core-cycle if exclude_selfrefs: # self_refs = kj.kjSet(g).ident() & g # g = g - self_refs g = g - kj.kjSet(g).ident() me._find(g)