Add edges between all atoms with the same atom_label in rings.
19661
def _add_label_edges(self):
        """"""
        labels = self.ast.select('atom_label')
        if not labels:
            return

        # We need each individual label and atoms with multiple ring labels
        # would yield e.g. the string '12' so split those up.
        label_digits = defaultdict(list)
        for label in labels:
            digits = list(label.tail[0])
            for digit in digits:
                label_digits[digit].append(label.parent())

        for label, (atom1, atom2) in label_digits.items():
            atom1_idx = self._atom_indices[id(atom1)]
            atom2_idx = self._atom_indices[id(atom2)]
            self.add_edge(atom1_idx, atom2_idx)
666613
def add_node(self, c):
        
        idx = len(self.nodes)
        self.edges[idx] = set()
        self.nodes.append(c)
        return idx
417289
def add_edge(self, u, v, **attr):
        
        if u not in self.vertices:
            self.vertices[u] = []
            self.pred[u] = []
            self.succ[u] = []
        if v not in self.vertices:
            self.vertices[v] = []
            self.pred[v] = []
            self.succ[v] = []
        vertex = (u, v)
        self.edges[vertex] = {}
        self.edges[vertex].update(attr)
        self.vertices[u].append(v)
        self.pred[v].append(u)
        self.succ[u].append(v)
707285
def iter_halfs_bend(graph):
    """"""
    for atom2 in range(graph.num_vertices):
        neighbors = list(graph.neighbors[atom2])
        for index1, atom1 in enumerate(neighbors):
            for atom3 in neighbors[index1+1:]:
                try:
                    affected_atoms = graph.get_halfs(atom2, atom1)[0]
                    # the affected atoms never contain atom1!
                    yield affected_atoms, (atom1, atom2, atom3)
                    continue
                except GraphError:
                    pass
                try:
                    affected_atoms = graph.get_halfs(atom2, atom3)[0]
                    # the affected atoms never contain atom3!
                    yield affected_atoms, (atom3, atom2, atom1)
                except GraphError:
                    pass
647909
def pistacking(rings_bs, rings_lig):
    """"""
    data = namedtuple(
        'pistack', 'proteinring ligandring distance angle offset type restype resnr reschain restype_l resnr_l reschain_l')
    pairings = []
    for r, l in itertools.product(rings_bs, rings_lig):
        # DISTANCE AND RING ANGLE CALCULATION
        d = euclidean3d(r.center, l.center)
        b = vecangle(r.normal, l.normal)
        a = min(b, 180 - b if not 180 - b < 0 else b)  # Smallest of two angles, depending on direction of normal

        # RING CENTER OFFSET CALCULATION (project each ring center into the other ring)
        proj1 = projection(l.normal, l.center, r.center)
        proj2 = projection(r.normal, r.center, l.center)
        offset = min(euclidean3d(proj1, l.center), euclidean3d(proj2, r.center))

        # RECEPTOR DATA
        resnr, restype, reschain = whichresnumber(r.atoms[0]), whichrestype(r.atoms[0]), whichchain(r.atoms[0])
        resnr_l, restype_l, reschain_l = whichresnumber(l.orig_atoms[0]), whichrestype(
            l.orig_atoms[0]), whichchain(l.orig_atoms[0])

        # SELECTION BY DISTANCE, ANGLE AND OFFSET
        passed = False
        if not config.MIN_DIST < d < config.PISTACK_DIST_MAX:
            continue
        if 0 < a < config.PISTACK_ANG_DEV and offset < config.PISTACK_OFFSET_MAX:
            ptype = 'P'
            passed = True
        if 90 - config.PISTACK_ANG_DEV < a < 90 + config.PISTACK_ANG_DEV and offset < config.PISTACK_OFFSET_MAX:
            ptype = 'T'
            passed = True
        if passed:
            contact = data(proteinring=r, ligandring=l, distance=d, angle=a, offset=offset,
                           type=ptype, resnr=resnr, restype=restype, reschain=reschain,
                           resnr_l=resnr_l, restype_l=restype_l, reschain_l=reschain_l)
            pairings.append(contact)
    return filter_contacts(pairings)
1273798
def relabel_atoms(self, start=1):
        
        counter = start
        for atom in self.get_atoms():
            atom.id = counter
            counter += 1
        return
332213
def _edge_both_nodes(nodes: List[Node]):
        """"""
        node_ids = [node.id for node in nodes]

        return and_(
            Edge.source_id.in_(node_ids),
            Edge.target_id.in_(node_ids),
        )
25356
def edges
      vertices.map { |vert| vert.successors.map { |succ| [vert, succ] }}.flatten 1
    end
1282418
def _prepare_atoms(topology, compute_cycles=False):
    """"""
    atom1 = next(topology.atoms())
    has_whitelists = hasattr(atom1, 'whitelist')
    has_cycles = hasattr(atom1, 'cycles')
    compute_cycles = compute_cycles and not has_cycles

    if compute_cycles or not has_whitelists:
        for atom in topology.atoms():
            if compute_cycles:
                atom.cycles = set()
            if not has_whitelists:
                atom.whitelist = OrderedSet()
                atom.blacklist = OrderedSet()

    if compute_cycles:
        bond_graph = nx.Graph()
        bond_graph.add_nodes_from(topology.atoms())
        bond_graph.add_edges_from(topology.bonds())
        all_cycles = _find_chordless_cycles(bond_graph, max_cycle_size=8)
        for atom, cycles in zip(bond_graph.nodes, all_cycles):
            for cycle in cycles:
                atom.cycles.add(tuple(cycle))
553259
public void placeRing(IRing ring, Point2d ringCenter, double bondLength, Map<Integer, Double> startAngles) {
        double radius = this.getNativeRingRadius(ring, bondLength);
        double addAngle = 2 * Math.PI / ring.getRingSize();

        IAtom startAtom = ring.getAtom(0);
        Point2d p = new Point2d(ringCenter.x + radius, ringCenter.y);
        startAtom.setPoint2d(p);
        double startAngle = Math.PI * 0.5;

        /*
         * Different ring sizes get different start angles to have visually
         * correct placement
         */
        int ringSize = ring.getRingSize();
        if (startAngles.get(ringSize) != null) startAngle = startAngles.get(ringSize);

        List<IBond> bonds = ring.getConnectedBondsList(startAtom);
        /*
         * Store all atoms to draw in consecutive order relative to the chosen
         * bond.
         */
        Vector<IAtom> atomsToDraw = new Vector<IAtom>();
        IAtom currentAtom = startAtom;
        IBond currentBond = (IBond) bonds.get(0);
        for (int i = 0; i < ring.getBondCount(); i++) {
            currentBond = ring.getNextBond(currentBond, currentAtom);
            currentAtom = currentBond.getOther(currentAtom);
            atomsToDraw.addElement(currentAtom);
        }
        atomPlacer.populatePolygonCorners(atomsToDraw, ringCenter, startAngle, addAngle, radius);
    }
1327580
private List<Integer> getBondNosForRingGroup(IAtomContainer molecule, List<Integer> ringGroup, IRingSet ringSet) {
        List<Integer> btc = new ArrayList<Integer>();
        for (Integer i : ringGroup) {
            for (IBond bond : ringSet.getAtomContainer(i).bonds()) {
                if (btc.size() > 0) {
                    if (!btc.contains(molecule.indexOf(bond))) {
                        btc.add(molecule.indexOf(bond));
                    }
                } else {
                    btc.add(molecule.indexOf(bond));
                }
            }
        }
        return btc;
    }
1274339
def iter_halfs_double(graph):
    """"""
    edges = graph.edges
    for index1, (atom_a1, atom_b1) in enumerate(edges):
        for atom_a2, atom_b2 in edges[:index1]:
            try:
                affected_atoms1, affected_atoms2, hinge_atoms = graph.get_halfs_double(atom_a1, atom_b1, atom_a2, atom_b2)
                yield affected_atoms1, affected_atoms2, hinge_atoms
            except GraphError:
                pass
1065909
def add_self_edges(self, weight=None, copy=False):
    ''''''
    ii = np.arange(self.num_vertices())
    return self.add_edges(ii, ii, weight=weight, symmetric=False, copy=copy)
441943
List<AtomPair> findCongestedPairs() {

        List<AtomPair> pairs = new ArrayList<>();

        // only add a single pair between each ring system, otherwise we
        // may have many pairs that are actually all part of the same
        // congestion
        Set<IntTuple> ringpairs = new HashSet<>();

        // score at which to check for crossing bonds
        final double maybeCrossed = 1.0 / (2 * 2);

        final int numAtoms = mol.getAtomCount();
        for (int u = 0; u < numAtoms; u++) {
            for (int v = u + 1; v < numAtoms; v++) {
                double contribution = congestion.contribution(u, v);
                // <0 = bonded
                if (contribution <= 0)
                    continue;

                // we don't modify ring bonds with the class to when the atoms
                // same ring systems we can't reduce the congestion
                if (ringsystems[u] > 0 && ringsystems[u] == ringsystems[v])
                    continue;

                // an un-bonded atom pair is congested if they're and with a certain distance
                // or any of their bonds are crossing
                if (contribution >= MIN_SCORE || contribution >= maybeCrossed && haveCrossingBonds(u, v)) {

                    int uWeight = mol.getAtom(u).getProperty(AtomPlacer.PRIORITY);
                    int vWeight = mol.getAtom(v).getProperty(AtomPlacer.PRIORITY);

                    int[] path = uWeight > vWeight ? apsp.from(u).pathTo(v)
                                                   : apsp.from(v).pathTo(u);

                    // something not right here if the len is < 3
                    int len = path.length;
                    if (len < 3) continue;

                    // build the seqAt and bndAt lists from shortest path
                    int[] seqAt = new int[len - 2];
                    IBond[] bndAt = new IBond[len - 1];
                    makeAtmBndQueues(path, seqAt, bndAt);

                    // we already know about this collision between these ring systems
                    // so dont add the pair
                    if (ringsystems[u] > 0 && ringsystems[v] > 0 &&
                            !ringpairs.add(new IntTuple(ringsystems[u], ringsystems[v])))
                        continue;

                    // add to pairs to overlap
                    pairs.add(new AtomPair(u, v, seqAt, bndAt));
                }
            }
        }

        // sort the pairs to attempt consistent overlap resolution (order independent)
        Collections.sort(pairs, new Comparator<AtomPair>() {
            @Override
            public int compare(AtomPair a, AtomPair b) {
                int a1 = atoms[a.fst].getProperty(AtomPlacer.PRIORITY);
                int a2 = atoms[a.snd].getProperty(AtomPlacer.PRIORITY);
                int b1 = atoms[b.fst].getProperty(AtomPlacer.PRIORITY);
                int b2 = atoms[b.snd].getProperty(AtomPlacer.PRIORITY);
                int amin, amax;
                int bmin, bmax;
                if (a1 < a2) {
                    amin = a1;
                    amax = a2;
                }
                else {
                    amin = a2;
                    amax = a1;
                }
                if (b1 < b2) {
                    bmin = a1;
                    bmax = a2;
                }
                else {
                    bmin = a2;
                    bmax = a1;
                }
                int cmp = Integer.compare(amin, bmin);
                if (cmp != 0) return cmp;
                return Integer.compare(amax, bmax);
            }
        });

        return pairs;
    }
1263587
private void placeMultipleGroups(IAtomContainer mol) {
        final List<Sgroup> sgroups = mol.getProperty(CDKConstants.CTAB_SGROUPS);
        if (sgroups == null)
            return;
        final List<Sgroup> multipleGroups = new ArrayList<>();
        for (Sgroup sgroup : sgroups) {
            if (sgroup.getType() == SgroupType.CtabMultipleGroup)
                multipleGroups.add(sgroup);
        }
        if (multipleGroups.isEmpty())
            return;

        int[][] adjlist = GraphUtil.toAdjList(mol);
        Map<IAtom,Integer> idxs = new HashMap<>();
        for (IAtom atom : mol.atoms())
            idxs.put(atom, idxs.size());

        for (Sgroup sgroup : multipleGroups) {
            final int numCrossing = sgroup.getBonds().size();
            if (numCrossing != 0 && numCrossing != 2)
                continue;

            // extract substructure
            final IAtomContainer substructure = mol.getBuilder().newInstance(IAtomContainer.class);
            final Set<IAtom> visit = new HashSet<>();
            final Collection<IAtom> patoms = sgroup.getValue(SgroupKey.CtabParentAtomList);
            if (patoms == null)
                continue;
            for (IAtom atom : patoms) {
                substructure.addAtom(atom);
                visit.add(atom);
            }
            for (IBond bond : mol.bonds()) {
                IAtom beg = bond.getBegin();
                IAtom end = bond.getEnd();
                if (visit.contains(beg) && visit.contains(end))
                    substructure.addBond(bond);
            }

            // advanced API usage, we make a set that only includes the atoms we want to match
            // and use this in a custom AtomMatcher to skip matches we don't want and update as
            // we go
            visit.addAll(sgroup.getAtoms());

            Pattern ptrn = VentoFoggia.findSubstructure(substructure, new AtomMatcher() {
                @Override
                public boolean matches(IAtom a, IAtom b) {
                    if (!visit.contains(b))
                        return false;
                    final int aElem = safeUnbox(a.getAtomicNumber());
                    final int bElem = safeUnbox(b.getAtomicNumber());
                    if (aElem != bElem)
                        return false;
                    final int aChg = safeUnbox(a.getFormalCharge());
                    final int bChg = safeUnbox(b.getFormalCharge());
                    if (aChg != bChg)
                        return false;
                    final int aMass = safeUnbox(a.getMassNumber());
                    final int bMass = safeUnbox(b.getMassNumber());
                    if (aMass != bMass)
                        return false;
                    final int aHcnt = safeUnbox(a.getImplicitHydrogenCount());
                    final int bHcnt = safeUnbox(b.getImplicitHydrogenCount());
                    if (aHcnt != bHcnt)
                        return false;
                    return true;
                }
            }, BondMatcher.forOrder());

            Set<IAtom> sgroupAtoms = sgroup.getAtoms();

            // when there are crossing bonds, things are more tricky as
            // we need to translate connected parts
            List<Map.Entry<Point2d,Vector2d>> outgoing = new ArrayList<>();
            List<Map.Entry<IBond,Vector2d>>   xBondVec = new ArrayList<>();
            if (numCrossing == 2) {
                for (IBond bond : mol.bonds()) {
                    IAtom beg = bond.getBegin();
                    IAtom end = bond.getEnd();
                    if (patoms.contains(beg) == patoms.contains(end))
                        continue;
                    if (patoms.contains(beg)) {
                        outgoing.add(new SimpleImmutableEntry<>(beg.getPoint2d(),
                                                                new Vector2d(end.getPoint2d().x - beg.getPoint2d().x,
                                                                             end.getPoint2d().y - beg.getPoint2d().y)));
                    } else {
                        outgoing.add(new SimpleImmutableEntry<>(end.getPoint2d(),
                                                                new Vector2d(beg.getPoint2d().x - end.getPoint2d().x,
                                                                             beg.getPoint2d().y - end.getPoint2d().y)));
                    }
                }
                for (IBond bond : sgroup.getBonds()) {
                    IAtom beg = bond.getBegin();
                    IAtom end = bond.getEnd();
                    if (sgroupAtoms.contains(beg)) {
                        xBondVec.add(new SimpleImmutableEntry<>(bond,
                                                                new Vector2d(end.getPoint2d().x - beg.getPoint2d().x,
                                                                             end.getPoint2d().y - beg.getPoint2d().y)));
                    } else {
                        xBondVec.add(new SimpleImmutableEntry<>(bond,
                                                                new Vector2d(beg.getPoint2d().x - end.getPoint2d().x,
                                                                             beg.getPoint2d().y - end.getPoint2d().y)));
                    }
                }
            }

            // no crossing bonds is easy just map the repeat part and transfer coordinates
            visit.removeAll(patoms); // don't need to map parent
            for (Map<IAtom, IAtom> atoms : ptrn.matchAll(mol).uniqueAtoms().toAtomMap()) {
                for (Map.Entry<IAtom, IAtom> e : atoms.entrySet()) {
                    e.getValue().setPoint2d(new Point2d(e.getKey().getPoint2d()));
                }
                // search is lazy so can update the matcher before the next match
                // is found (implementation ninja)
                visit.removeAll(atoms.values());
            }

            // reposition
            assert xBondVec.size() == outgoing.size();
            for (Map.Entry<IBond,Vector2d> e : xBondVec) {
                IBond bond = e.getKey();

                // can't fix move ring bonds
                if (bond.isInRing())
                    continue;

                IAtom beg  = sgroupAtoms.contains(bond.getBegin()) ? bond.getBegin() : bond.getEnd();
                Map.Entry<Point2d,Vector2d> best = null;
                for (Map.Entry<Point2d,Vector2d> candidate : outgoing) {
                    if (best == null || candidate.getKey().distance(beg.getPoint2d()) < best.getKey().distance(beg.getPoint2d()))
                        best = candidate;
                }
                outgoing.remove(best);
                assert best != null;

                // visit rest of connected molecule
                Set<Integer> iVisit = new HashSet<>();
                iVisit.add(idxs.get(beg));
                visit(iVisit, adjlist, idxs.get(bond.getOther(beg)));
                iVisit.remove(idxs.get(beg));
                IAtomContainer frag = mol.getBuilder().newInstance(IAtomContainer.class);
                for (Integer idx : iVisit)
                    frag.addAtom(mol.getAtom(idx));

                Vector2d orgVec = e.getValue();
                Vector2d newVec = best.getValue();

                Point2d endP    = bond.getOther(beg).getPoint2d();
                Point2d newEndP = new Point2d(beg.getPoint2d());
                newEndP.add(newVec);

                // need perpendicular dot product to get signed angle
                double pDot  = orgVec.x * newVec.y - orgVec.y * newVec.x;
                double theta = Math.atan2(pDot, newVec.dot(orgVec));

                // position
                GeometryUtil.translate2D(frag, newEndP.x - endP.x, newEndP.y - endP.y);
                GeometryUtil.rotate(frag, new Point2d(bond.getOther(beg).getPoint2d()), theta);
            }
        }

    }
470656
def edges2nodes(edges):
    """"""
    nodes = []
    for e1, e2 in edges:
        nodes.append(e1)
        nodes.append(e2)
    nodedict = dict([(n, None) for n in nodes])
    justnodes = list(nodedict.keys())
    # justnodes.sort()
    justnodes = sorted(justnodes, key=lambda x: str(x[0]))
    return justnodes
70614
def invariants(mol):
    """"""
    atom_ids = {}
    for a in mol.atoms:
        components = []
        components.append(a.number)
        components.append(len(a.oatoms))
        components.append(a.hcount)
        components.append(a.charge)
        components.append(a.mass)
        if len(a.rings) > 0:
            components.append(1)

        atom_ids[a.index] = gen_hash(components)

    return atom_ids