Ejemplo n.º 1
0
def within(resnum, angstroms, chain_id, model, use_ca=False, custom_coord=None):
    """See: https://www.biostars.org/p/1816/ https://www.biostars.org/p/269579/

    Args:
        resnum (int):
        angstroms (float):
        chain_id (str):
        model (Model):
        use_ca (bool): If the alpha-carbon atom should be used for the search, otherwise use the last atom of the residue
        custom_coord (list): Custom XYZ coordinate to get within

    Returns:
        list: List of Bio.PDB.Residue.Residue objects

    """
    # XTODO: documentation
    # TODO: should have separate method for within a normal residue (can use "resnum" with a int) or a custom coord,
    # where you don't need to specify resnum
    atom_list = Selection.unfold_entities(model, 'A')
    ns = NeighborSearch(atom_list)

    if custom_coord:  # a list of XYZ coord
        target_atom_coord = np.array(custom_coord, 'f')
    else:
        target_residue = model[chain_id][resnum]
        if use_ca:
            target_atom = target_residue['CA']
        else:
            target_atom = target_residue.child_list[-1]
        target_atom_coord = np.array(target_atom.get_coord(), 'f')
    neighbors = ns.search(target_atom_coord, angstroms)
    residue_list = Selection.unfold_entities(neighbors, 'R')

    return residue_list
Ejemplo n.º 2
0
	def __init__(self, structure, chain_id, threshold):
		ns = NeighborSearch(list(structure.get_atoms()))

		for chain in structure[0]:
			if chain.id == chain_id:
				for residue in chain:
					if residue.id[0] == ' ':
						inter = 0
						intra = 0
						lon = 0
						shor = 0
	
	
						center = get_center(residue)
						for a in ns.search(center, threshold):  # Iterate over contacts
							if a.get_full_id()[2] == residue.get_full_id()[2]:
								#if abs(int(a.get_full_id()[1]) - int(residue.get_full_id()[1])) > 3:
								intra += 1
							else:
								inter += 1
							if np.linalg.norm(a.get_coord()-center) < threshold/2:
								shor += 1
							else:
								lon += 1
						self.contacts[residue.get_full_id()] = (inter, intra, lon, shor)
Ejemplo n.º 3
0
    def search_subs(
        self,
        hx_atom,
        cx_atom,
        cy_atom,
        hy_atom,
        j_atoms,
        chosen_j
    ):
        """ Description:

            Usage:

            Parameters:
        """

        subs_list = []
        # j_atoms = [j[0] for j in j_atoms]
        center = self.atom_dict[cy_atom][2]
        ns = NeighborSearch(self.atom_list)
        neighbors = ns.search(center, 1.7)
        for neigh_atom in neighbors:
            if neigh_atom.serial_number not in j_atoms:
                subs_list.append(neigh_atom)

        for subs in subs_list:
            self.j_dict[chosen_j]["substituents"][subs.serial_number] = {
                "SY": self.atom_dict[subs.serial_number][0],
                "HX": self.atom_dict[hx_atom][0],
                "CX": self.atom_dict[cx_atom][0],
                "CY": self.atom_dict[cy_atom][0],
                "element": self.atom_dict[subs.serial_number][1]
            }
def filter_structure(pdb,chain,lig,lig_num):
  # pdb_input = pdb_path + "/" + pdb + ":" + chain + ":" + lig + ":" + lig_num + ".atoms.pdb"
  pdb_input = pdb_path + "/" + pdb + ".pdb"
  pdb_output = output_path + "/" + pdb + ":" + chain + ":" + lig + ":" + lig_num + ".atoms.pdb"
  
  structure = PDBParser(QUIET=1).get_structure(pdb, pdb_input)
  atoms_pairs = NeighborSearch( list( structure.get_atoms() ) ).search_all(search_radius)

  res_list = set()

  for atom_pair in atoms_pairs:
    res1 = atom_pair[0].parent
    res_chain1 = res1.parent.id
    res_name1 = res1.resname
    res_num1 =  str(res1.id[1])  
  
    res2 = atom_pair[1].parent
    res_chain2 = res2.parent.id
    res_name2 = res2.resname
    res_num2 = str(res2.id[1])

    if ( (res_chain1 == chain and res_name1 == lig and res_num1 == lig_num) or (res_chain2 == chain and res_name2 == lig and res_num2 == lig_num) ):    
      res_list.add(res1)
      res_list.add(res2)  

  io = PDBIO()
  io.set_structure(structure)
  io.save(pdb_output, ResSelect(res_list))
Ejemplo n.º 5
0
 def interchain_residue_contacts(self, chain_ids_1, chain_ids_2, radius):
     """ Generate a list of residue contacts between two chains. """
     all_chains = {chain.get_id(): chain for chain in self.get_chains()}
     selected_chains = {
         chain_id: chain
         for chain_id, chain in all_chains.items()
         if chain_id in chain_ids_1 + chain_ids_2
     }
     atoms = [
         atom for chain_id, chain in selected_chains.items()
         for atom in Selection.unfold_entities(chain, "A")
     ]
     residue_contacts = NeighborSearch(atoms).search_all(radius, "R")
     classified_contacts = defaultdict(list)
     for contact in residue_contacts:
         chain_1, chain_2 = [
             residue.get_parent().get_id() for residue in contact
         ]
         if chain_1 in chain_ids_1 and chain_2 in chain_ids_2:
             classified_contacts[(chain_1, chain_2)].append({
                 chain_1:
                 contact[0],
                 chain_2:
                 contact[1]
             })
         elif chain_2 in chain_ids_1 and chain_1 in chain_ids_2:
             classified_contacts[(chain_2, chain_1)].append({
                 chain_1:
                 contact[0],
                 chain_2:
                 contact[1]
             })
     return classified_contacts
Ejemplo n.º 6
0
def pdb_neighbors(pdb_f, pdb_id):
    structure = PDBParser().get_structure(pdb_id, pdb_f)
    atom_list = Selection.unfold_entities(structure, 'A')
    ns = NeighborSearch(atom_list)
    center_res = [res for res in structure.get_residues() if res.get_resname() in ['PTR','SEP','TPO']]

    neighbors = []
    for res in center_res:
        if res.get_resname() == 'PTR':
            atoms = [atom for atom in res.child_list if atom.get_name() in ['O1P', 'O2P', 'O3P', 'OH']]
        elif res.get_resname() == 'SEP':
            atoms = [atom for atom in res.child_list if atom.get_name() in ['O1P', 'O2P', 'O3P', 'OG']]
        elif res.get_resname() == 'TPO':
            atoms = [atom for atom in res.child_list if atom.get_name() in ['O1P', 'O2P', 'O3P', 'OG1']]
        atom_neighbors = [ns.search(a.get_coord(),BOND_CUTOFF) for a in atoms]
        atom_neighbors = [atom for atoms in atom_neighbors for atom in atoms]
        atom_neighbors = list(set(atom_neighbors))
        atom_neighbors = [atom for atom in atom_neighbors if 'N' in atom.get_name() or 'O' in atom.get_name()]
        atom_neighbors = list(set(Selection.unfold_entities(atom_neighbors,'R')))
        atom_neighbors = [r for r in atom_neighbors if r != res]

        if len(atom_neighbors) > 0:
            res = res.get_resname()+'_'+str(res.get_id()[1])+'_'+res.get_parent().get_id()
            atom_neighbors = [n.get_resname()+'_'+str(n.get_id()[1])+'_'+n.get_parent().get_id() for n in atom_neighbors]
            neighbors.append((pdb_id,res,atom_neighbors))

    return neighbors
Ejemplo n.º 7
0
    def contact_pairs(self):
        """obtain all residue pairs with atoms in close proximity"""

        radius = 4.5
        ns = NeighborSearch(self.atom_list)
        self.contact_pairs = ns.search_all(radius,
                                           level='R')  #residues returned
Ejemplo n.º 8
0
def pdb_dist(pdb_f, pdb_id):
    structure = PDBParser().get_structure(pdb_id, pdb_f)
    atom_list = Selection.unfold_entities(structure, 'A')
    ns = NeighborSearch(atom_list)
    center = [a for a in structure.get_atoms() if a.get_parent().get_resname(
    ) in ['PTR', 'SEP', 'TPO'] and a.get_name() in ['O1P', 'O2P', 'O3P', 'OH', 'OG', 'OG1']]

    # neighbors = [a for a in structure.get_atoms() if a.get_parent().get_resname(
    # ) in ['ARG'] and a.get_name() in ['NE', 'NH2', 'NH1']]
    # neighbors = [a for a in structure.get_atoms() if a.get_parent().get_resname(
    # ) in ['Lys'] and a.get_name() in ['NZ']]
    neighbors = [a for a in structure.get_atoms() if a.get_parent().get_resname(
    ) in ['HIS'] and a.get_name() in ['ND1','NE2']]

    def calc_dist(a, b):
        vector = a.coord - b.coord
        return np.sqrt(np.sum(vector * vector))

    dist = {}
    for c in center:
        for n in neighbors:
            value = calc_dist(c, n)
            key = str(c.get_parent()) + '_' + str(n.get_parent())
            if not key in dist.keys():
                dist[key] = [value]
            else:
                dist[key].append(value)

    for k, v in dist.items():
        dist[k] = min(v)

    dist = [v for k, v in dist.items()]

    return dist
Ejemplo n.º 9
0
def pdb_neighbors(pdb_f, pdb_id):
    structure = PDBParser().get_structure(pdb_id, pdb_f)
    atom_list = Selection.unfold_entities(structure, 'A')
    ns = NeighborSearch(atom_list)
    center = [(a, a.get_coord()) for a in structure.get_atoms()
              if a.get_parent().get_resname() in ['PTR', 'SEP', 'TPO']
              and a.get_name() in ['O1P', 'O2P', 'O3P', 'OH', 'OG', 'OG1']]
    # if there are no phos-atomes, return
    if len(center) == 0:
        return ''
    neighbors = {}
    for a, c in center:
        # set neighbor distance cutoff
        neighbor_list = ns.search(c, BOND_CUTOFF)
        residue_list = list(set(Selection.unfold_entities(neighbor_list, 'R')))
        try:
            neighbors[Selection.unfold_entities(a, 'R')[0]] = [
                x for x in residue_list
                if not x == Selection.unfold_entities(a, 'R')[0]
            ]
        except:
            continue
    # add residue id and chain id
    neighbors_full = dict([('_'.join(
        [k.get_resname(),
         str(k.get_id()[1]),
         str(k.get_parent().get_id())]), [
             '_'.join([
                 vi.get_resname(),
                 str(vi.get_id()[1]),
                 str(vi.get_parent().get_id())
             ]) for vi in v
         ]) for k, v in neighbors.iteritems()])
    return neighbors_full
Ejemplo n.º 10
0
def CheckClashes(structure, chain):
    """
    Checks for clashes at a radius = 2 between a PDB structure and all the atoms on the provided chain.
    Returns True or False depending if number of different residues clashing exceeds 25.
    Arguments:
        -structure: PDB structure.
        -chain: PDB chain structure to check if it has clashes with the main structure.
    """
    # declare NeighborSearch() object instance with all the atoms from the structure (model 0), that includes all chains of that structure.
    ns = NeighborSearch(unfold_entities(structure[0], 'A'))

    # iterate over atoms in input chain, search for close residues
    clashing_residues = set([])
    for atom in chain.get_atoms():
        close_res = ns.search(atom.get_coord(), radius=2, level="R")

        try:
            close_res.remove(atom.get_parent())
        except ValueError:
            pass

        for res in close_res:
            neighbor_res = (atom.get_parent(), res)
            clashing_residues.add(neighbor_res)
            if len(clashing_residues) > 25:
                return True

    return False
Ejemplo n.º 11
0
def get_neighbor_chains(structure, options):
    """
    Takes an structure and returns a dictionary with chains as keys and a list of chains as values holding the
    chains with alpha carbons at less than 8 amstrongs from an alpha carbon of the key chain
    :param structure: structure we want to check for clashes.
    :return: dictionary with the clashes between chains.
    """

    neighbor_chains = {}
    ns = NeighborSearch(list(structure.get_atoms()))
    for chain in structure.get_chains():
        chains = list(structure.get_chains())
        neighbor_chains[chain] = set([])

        neighbor_dict = {}
        for atom in [atom for atom in chain.get_atoms() if
                     atom.get_id() == 'CA' or atom.get_id() == 'P']:  # For every alpha carbon or P in chain
            for atom2 in ns.search(atom.get_coord(), 8, level='A'):
                if atom2.get_id() == 'CA' or atom2.get_id() == 'P':  # for every alpha carbon or P at 8 angstroms or less from atom
                    chain2 = atom2.get_parent().get_parent()  # Getting to which chain it belongs
                    if chain2 != chain and chain2 not in neighbor_chains.keys():
                        # If it is not in the same chain and it is not already assessed
                        if chain2 not in neighbor_dict:
                            neighbor_dict[chain2] = 0
                        neighbor_dict[chain2] += 1

        if options.verbose:
            print('\n%s' % chain)
            for close_chain, contacts in neighbor_dict.items():
                print('%s: %s' % (close_chain, contacts))
                if contacts > 8:
                    neighbor_chains[chain].add(close_chain)
    return neighbor_chains
Ejemplo n.º 12
0
    def search_stacking(self):
        """ KC - stacking research in model """

        #KC#CG# list of aromatics residues atoms
        atom_for_search = []
        for res in self.model.res:
            if res.resname in ['PHE', 'TYR', 'TRP', 'HIS']:
                for name in parametres.dico_cycles[res.resname]["cycle"]:
                    atom_for_search.append(res[name])

        #KC#CG# list of residues pairs that have atoms pairs within 6A radius
        self.aromatic_less_5 = NeighborSearch(atom_for_search).search_all(
            6, level='R')

        #KC#CG# search of stacking
        self.stacking = []
        for res1, res2 in self.aromatic_less_5:
            if is_stacking(res1, res2):
                if res1.get_id()[1] < res2.get_id()[1]:
                    self.stacking.append((res1, res2))
                else:
                    self.stacking.append((res2, res1))

        self.stacking_networks = self.search_network(self.stacking,
                                                     _type='stacking')
Ejemplo n.º 13
0
def get_residues_distance_distribution(data, r):
    """
    This function computes the distribution of number of residues in certain radius around residues.

    """
    files = glob.glob(data + "*_b.pdb")
    dist = {}
    files.sort()
    file_counter = 0
    for bound_pbd in files:
        dist[bound_pbd] = []
    l = []
    for bound_pbd in files:
        file_counter += 1
        print "Protein " + str(file_counter) + "/" + str(len(files))
        s, a, r = read_pdb_file(bound_pbd)
        ns = NeighborSearch(a)
        res_counter = 0
        for res in r:
            b = 0 * res.child_list[0].get_coord()
            for atom in res.child_list:
                b += atom.get_coord()
            center = b / len(res.child_list)
            l.append(len(ns.search(center, 100, "R")))
            res_counter += 1
            # print "Residue " + str(res_counter) + "out of " + str(len(r))
    plot(np.bincount(l))
    show()
    print files
Ejemplo n.º 14
0
    def collectSaltBridge(self, position, chain):
        model = self.structure[0]
        myres = model[chain][position]
        atoms = Selection.unfold_entities(model, 'A')  # A for atoms

        ns = NeighborSearch(atoms)
        if myres.get_resname() not in ['ARG', 'LYS', 'ASP', 'GLU', 'HIS']:
            is_sb = 0
        else:
            for atom in myres:
                atom_id = atom.get_full_id()
                if atom_id[4][0] in ['NH1', 'NH2', 'NZ', 'NE2']:
                    close_atoms = ns.search(
                        atom.coord, 4.5
                    )  # cutoff of 4 crieria fixed by Barlow, J M Thornton (PMID6887253) +0.5A to account for the unoptimised side chain
                    if any(atom in [atomtype.id for atomtype in close_atoms]
                           for atom in ['OE1', 'OE2', 'OD1', 'OD2']):
                        is_sb = 1
                        break
                    else:
                        is_sb = 0
                        break
                elif atom_id[4][0] in ['OE1', 'OE2', 'OD1', 'OD2']:
                    close_atoms = ns.search(atom.coord, 4.5)

                    if any(atom in [atomtype.id for atomtype in close_atoms]
                           for atom in ['NH1', 'NH2', 'NZ', 'NE2']):
                        is_sb = 1
                        break
                    else:
                        is_sb = 0
                        break
        return is_sb
Ejemplo n.º 15
0
    def search_connectivity(self, atom_center, rank, NS=None, previous=None):

        if NS is None:
            NS = NeighborSearch(self.model.atoms)

        resultat = [
            atom for atom in NS.search(center=atom_center.get_coord(),
                                       radius=parametres.cutoff_bonds,
                                       level="A")
            if atom not in [atom_center, previous]
        ]

        if rank == 1:
            return resultat
        else:
            connectivity = {}
            for atom in resultat:
                resultat_temp = self.search_connectivity(atom_center=atom,
                                                         rank=rank - 1,
                                                         NS=NS,
                                                         previous=atom_center)
                if len(resultat_temp) == 0:
                    connectivity[atom] = None
                else:
                    connectivity[atom] = resultat_temp
            return connectivity
Ejemplo n.º 16
0
 def collectHbondsNumber(self, foldxIndivFile):
     wt_mut_chain_id = whatMutation(foldxIndivFile)
     prot_chain = wt_mut_chain_id[3]
     prot_mut_id = int(wt_mut_chain_id[2])
     model = self.structure[0]
     myres = model[prot_chain][prot_mut_id]
     atoms = Selection.unfold_entities(model, 'A')  # A for atoms
     ns = NeighborSearch(atoms)
     resname = myres.get_resname()
     h_bond_as_donor = []
     h_bond_as_acceptor = []
     for atom in myres:
         if atom.name in donors:
             #atoms  = Selection.unfold_entities(model, 'A')
             #print(atoms)
             # cutoff of 3.2 angstroms D-A, strong mostly covalent according to
             # Jeffrey, George A.; An introduction to hydrogen bonding, Oxford University Press, 1997.
             close_atoms = ns.search(atom.coord, 3.2)
             for close_atom in close_atoms:
                 full_atom_id = close_atom.get_full_id()
                 if (full_atom_id[3][1] != prot_mut_id) and (
                         full_atom_id[4][0]
                         in acceptors + main_chain_acceptors):
                     acceptor_atom_id = full_atom_id[3][1]
                     h_bond_as_donor.append(acceptor_atom_id)
         # do the same thing fro acceptor atoms
         if atom.name in acceptors:
             close_atoms = ns.search(atom.coord, 3.2)
             for close_atom in close_atoms:
                 full_atom_id = close_atom.get_full_id()
                 if (full_atom_id[3][1] != prot_mut_id) and (
                         full_atom_id[4][0] in donors + main_chain_donors):
                     acceptor_atom_id = full_atom_id[3][1]
                     h_bond_as_acceptor.append(acceptor_atom_id)
     return len(h_bond_as_donor) + len(h_bond_as_acceptor)
Ejemplo n.º 17
0
 def __calculate_separate_simbox_statistics(self, component, radius): #, cells_taken_by_component):
     """
     calculates the number of grid cells describing each complex component.
     calculation is done when all components are located in the center of simulation box
     """
     self.cells_taken_by_component = {}
     grid = Grid("cubic", radius, 10*radius, -1.)
     grid.calculate_boundaries(component.pyrystruct.struct)
     grid.generate_cubic_grid([])
     
     #scitree = scipyconverter(grid.grid_cells)
     ns = NeighborSearch(grid.grid_cells)
                 
     for atom in component.pyrystruct.struct.get_atoms():
         center = array([atom.coord[0], atom.coord[1], atom.coord[2]])
         if atom.vdw <= radius: rad = radius* sqrt(3)
         else: rad = (radius*sqrt(3)) + atom.vdw
         neighbours = ns.search(center, rad, 'A') #atom.vdw + radius
         #neighbours = scitree.run_neisearch(center, rad, eps=0)
         self.cells_taken_by_component = self.__calculate_simbox_statistics(neighbours) #, cells_taken_by_component)
         if len(neighbours) == 0: print "OMGOMG"*10, component.pyrystruct.chain, atom.serial_number
      
     del grid
     del ns
     neighbours = []
     return len(self.cells_taken_by_component)
def _get_contacts(pdb_path, chain_rec, chain_lig, contact_dist):
    structure = pdb_parser.get_structure('X', pdb_path)[0]

    receptor = [structure[chain_rec_id] for chain_rec_id in chain_rec]
    ligand = [structure[chain_lig_id] for chain_lig_id in chain_lig]

    receptor_atoms = Selection.unfold_entities(receptor, 'A')
    ns = NeighborSearch(receptor_atoms)

    ligand_residues = Selection.unfold_entities(ligand, 'R')
    contacts = set([])
    contacts_lig = set([])
    contacts_rec = set([])
    for ligand_res in ligand_residues:
        lig_resname = dindex_to_1[d3_to_index[ligand_res.get_resname()]]
        lig_resnum = ligand_res.get_id()[1]
        lig_chname = ligand_res.get_parent().get_id()
        res_contacts = []

        for lig_atom in ligand_res:
            neighbors = ns.search(lig_atom.get_coord(), contact_dist)
            res_contacts += Selection.unfold_entities(neighbors, 'R')

        for receptor_res in res_contacts:
            rec_resname = dindex_to_1[d3_to_index[receptor_res.get_resname()]]
            rec_resnum = receptor_res.get_id()[1]
            rec_chname = receptor_res.get_parent().get_id()

            contacts.add((rec_resname, rec_resnum, rec_chname, lig_resname,
                          lig_resnum, lig_chname))
            contacts_lig.add((lig_resname, lig_resnum, lig_chname))
            contacts_rec.add((rec_resname, rec_resnum, rec_chname))

    return contacts, contacts_rec, contacts_lig
Ejemplo n.º 19
0
def calculate_ic(structure, d_cutoff=5.0, selection=None):
    """
    Calculates intermolecular contacts in a parsed structure object.
    """
    atom_list = list(structure.get_atoms())
    ns = NeighborSearch(atom_list)
    all_list = ns.search_all(radius=d_cutoff, level="R")

    if selection:
        _sd = selection

        def _chain(x):
            return x.parent.id

        ic_list = [
            c for c in all_list
            if (_chain(c[0]) in _sd and _chain(c[1]) in _sd) and (
                _sd[_chain(c[0])] != _sd[_chain(c[1])])
        ]
    else:
        ic_list = [c for c in all_list if c[0].parent.id != c[1].parent.id]

    if not ic_list:
        raise ValueError("No contacts found for selection")

    return ic_list
Ejemplo n.º 20
0
    def save_structure(self, output_dir="", remove_disordered=False):
        if remove_disordered:
            self._unset_disordered_flags()

        io = PDBIO()
        io.set_structure(self.structure)

        try:
            # Save all chains together
            outFile = op.join(output_dir,
                              self.pdb_id + "".join(self.chain_ids) + ".pdb")
            io.save(outFile)
            if len(self.chain_ids) > 1:
                # Save each chain individually
                for chain_id in self.chain_ids:
                    chain = self.structure[0][chain_id]
                    if chain_is_hetatm(chain):
                        continue
                    outFile = op.join(output_dir,
                                      self.pdb_id + chain_id + ".pdb")
                    atom_list = [
                        atom
                        for atom in self.structure[0][chain_id].get_atoms()
                    ]
                    hetatm_chain_ns = NeighborSearch(atom_list)
                    select = SelectChains(chain_id, self.hetatm_chain_id,
                                          hetatm_chain_ns, self.r_cutoff)
                    io.save(outFile, select=select)
            if len(self.chain_ids) > 2:
                # Save each interacting chain pair.
                for chain_ids in self.interacting_chain_ids:
                    outFile = op.join(
                        output_dir, self.pdb_id + "".join(chain_ids) + ".pdb")
                    atom_list = [
                        atom
                        for atom in self.structure[0][chain_id].get_atoms()
                        for chain_id in chain_ids
                    ]
                    hetatm_chain_ns = NeighborSearch(atom_list)
                    select = SelectChains(chain_ids, self.hetatm_chain_id,
                                          hetatm_chain_ns, self.r_cutoff)
                    io.save(outFile, select=select)

        except AttributeError as e:
            if remove_disordered:
                raise (e)
            self.save_structure(output_dir=output_dir, remove_disordered=True)
Ejemplo n.º 21
0
def check_clash(str_name, v=False):
    """check_clash, fract of clashes!

        if zero contacts then error -> fix ->

        Problem, contacts, str_name: 311 505 na-prot_13536.pdb
        Sterical clashes  0.615841584158

        c is counter
        """
    if v: print('fn:', str_name)
    structure = open(str_name)
    #model = structure[0]
    atoms_A = []
    atoms_B = []
    for line in structure.readlines():
        if line[:4] == "ATOM":
            #print line
            at_nam = line[12:16].strip()
            coor = [float(line[30:38]), float(line[38:46]), float(line[46:54])]
            at = Atom.Atom(at_nam, coor, 0.0, 1.0, ' ', at_nam, 1, at_nam[0])
            if line[21] == "A":
                atoms_A.append(at)
            elif line[21] == "B":
                atoms_B.append(at)
            else:
                pass
    #atoms_B = Selection.unfold_entities(structure[0]['B'], 'A')
    #print len(atoms_A), len(atoms_B)
    if len(atoms_A) > len(atoms_B):
        less = atoms_B
        more = atoms_A
    else:
        less = atoms_A
        more = atoms_B
    problem = 0
    contacts = 0
    ns = NeighborSearch(more)
    for at in less:
        neighbors = ns.search(array(at.get_coord()), 2.0, 'A')
        if neighbors != []:
            problem += 1
            contacts += 1
        else:
            neighbors1 = ns.search(array(at.get_coord()), 4.0, 'A')
            if neighbors1 != []:
                contacts += 1
    if v:
        print('problem:', float(problem))
        print('contacts:', float(contacts))
    try:
        fract = float(problem) / float(contacts)
    except ZeroDivisionError:
        fract = problem  # or skip this structure
        if v: print('ZeroDivison -- skip:', problem, contacts, str_name)
        return fract

    #print 'Contacts, str_name:', problem, contacts, str_name, "Sterical clashes ", fract
    return fract
Ejemplo n.º 22
0
    def set_simbox_with_no_shape_descriptor(self, fcomplex, start_orient,
                                            grid_radius, grid_type):
        """
	   when modeling is performed with no shape descriptor,
	   simulation box is calculated based on complex sequence volume
	"""
        ###############sprawdzic jednostke objetosci!!!!!!!!!!!!!!!!!!!!!!!
        vertex = round(fcomplex.volume**(1.0 / 3), 4)
        self.mapcuboid = MapCuboid([], [], [], grid_radius)

        #if start_orient == True:
        #assign minimal cuboid on current complex
        xcoords, ycoords, zcoords = [], [], []
        for comp in fcomplex.components:
            for atom in comp.pyrystruct.struct.get_atoms():
                if atom.coord[0] not in xcoords: xcoords.append(atom.coord[0])
                if atom.coord[1] not in ycoords: ycoords.append(atom.coord[1])
                if atom.coord[2] not in zcoords: zcoords.append(atom.coord[2])
        self.mapcuboid = MapCuboid(xcoords, ycoords, zcoords, grid_radius)
        self.mapcuboid.assign_cuboid_values()

        #else:
        #    self.mapcuboid = MapCuboid([],[],[], grid_radius)
        #    one_fixed, index,cuboid_center = False, 0, [0.,0.,0.]
        #    for component in fcomplex.components:
        #	if component.moves.state == "fixed" or component.moves.limited == True:
        #	    print "vector!", cuboid_center, component.mass_centre
        #	    cuboid_center = [cuboid_center[0] + component.mass_centre[0],\
        #			     cuboid_center[1] + component.mass_centre[1],\
        #	                     cuboid_center[2] + component.mass_centre[2] ]
        #	    one_fixed = True
        #	index += 1
        #break
        #
        ##set lat component as cuboid position descriptor
        #if not one_fixed: cuboid_center = component.mass_centre
        #
        #self.mapcuboid.center = [cuboid_center[0]/index,cuboid_center[1]/index,cuboid_center[2]/index ] #[0., 0., 0.]
        #print "mapcoboid centre", self.mapcuboid.center
        #self.mapcuboid.get_cuboid_coords(vertex)
        #self.mapcuboid.get_max_distance()
        #self.mapcuboid.set_edges_lengths()

        self.mapgrid = Grid(grid_type, grid_radius, 2 * grid_radius, -1.)


        self.mapgrid.set_xyz_ranges(self.mapcuboid.xmin, self.mapcuboid.xmax,\
               self.mapcuboid.ymin, self.mapcuboid.ymax,\
               self.mapcuboid.zmin, self.mapcuboid.zmax)

        #self.mapgrid.generate_cubic_grid(self.mappoints, self.map_radius)

        #self.mapgrid.set_map_threshold(self.map_threshold)
        #self.density_sum = self.mapgrid.get_map_density_sum()

        if self.mapgrid.mapcells:
            self.ns_mapgrid = NeighborSearch(self.mapgrid.mapcells)
        else:
            self.ns_mapgrid = []
Ejemplo n.º 23
0
def compute_interaction_center(pdb_file, mutation_site):
    """Computes the geometric center of all heavy atoms interacting with the mutated residue.
    
    Parameters
    ----------
    pdb_file : str
        Path to the PDB file containing the structure of the protein.
        
    mutation_size : int
        An integer designating the residue sequence ID.
        
    Returns
    -------
    NumPy ndarray
        The Cartesian coordinates of the geometric center
    """
    pdb_parser = PDBParser(PERMISSIVE=1)
    model = pdb_parser.get_structure(id='tmp', file=pdb_file)
    
    # get all heavy atoms of the protein
    all_heavy_atoms = [a for a in model.get_atoms() if a.element != 'H']
    
    # get the mutated residue
    mutation_res = None
    for res in model.get_residues():
        if res.get_id()[1] == int(mutation_site):
            mutation_res = res
            break
    
    # get sidechain atoms
    if mutation_res is not None:
        heavy_atoms = [a for a in mutation_res.get_list() if a.element != 'H']
        # if only four heavy atoms, aka, GLY, use CA
        if len(heavy_atoms) == 4:
            side_chain_atoms = [heavy_atoms[1]]
        else:
            side_chain_atoms = mutation_res.get_list()[4:]
    else:
        print('Invalid mutation site: {}'.format(mutation_site))
        sys.exit(1)
        
    # search for neighbnoring atoms
    ns = NeighborSearch(atom_list=all_heavy_atoms, bucket_size=10)
    all_interaction_atoms = []
    for a in side_chain_atoms:
        interaction_atoms = ns.search(center=a.coord, radius=5, level='A')
        all_interaction_atoms += interaction_atoms
    # remove duplicates
    all_interaction_atoms = set(all_interaction_atoms)
    
    # compute geometric center of all interaction atoms
    geometric_center = np.zeros((3,))
    for a in all_interaction_atoms:
        geometric_center += a.coord / len(all_interaction_atoms)

    return geometric_center
Ejemplo n.º 24
0
    def make_neighbors(self, fl_struct):
        # create an empty NeighborsNet
        nn = NeighborsNet()
        # use NeighborSearch from Bio.PDB to compute distances
        ns = NeighborSearch(list(self.bio_struct.get_atoms()))
        # for each chain in structure that is not a dna-rna one
        for fl_chain in fl_struct.get_chains():
            if not fl_chain.rna_dna_chain:
                # for each residue in this chain
                for fl_res in fl_chain.residues:
                    # add a default entry
                    nn.add_default(fl_res)
                    # keep track of already inserted nieghbors (the search is mate for each atom in the residue)
                    already_have = []
                    # for each atom (coordinates) in the residue
                    for atom_coord in fl_res.atoms_coord:
                        # for each residue in range
                        for res in ns.search(atom_coord,
                                             self.config["neighbors_range"],
                                             level='R'):
                            # check if it is good atom and the same model, cause sometimes NS computes all models
                            if is_good_res(
                                    res) and fl_res.model_id == res_model_id(
                                        res) and not res.get_full_id(
                                        ) in already_have:
                                # try to get FlipperResidueAssociated
                                pos_2 = fl_struct.chains[res_chain_id(
                                    res)].string_index_map.get(
                                        res_string_index(res))
                                # print(fl_res.get_full_identifier(), res.get_full_id(), fl_struct.chains[res_chain_id(res)].string_index_map.get(res_string_index(res)))
                                if not pos_2 == None:
                                    fl_res_2 = fl_struct.chains[res_chain_id(
                                        res)].residues[pos_2]
                                    # if the chain is the same
                                    if fl_res.chain_id == fl_res_2.chain_id:
                                        already_have.append(res.get_full_id())
                                        if fl_res.pos_in_chain == fl_res_2.pos_in_chain:
                                            continue
                                        # if distance (as residue number) is less than threshold, then it is a short range neighbor
                                        if abs(
                                                fl_res.pos_in_chain -
                                                fl_res_2.pos_in_chain
                                        ) < self.config[
                                                "long_short_threshold"] and not fl_chain.have_gaps(
                                                    fl_res, fl_res_2):
                                            nn.add_short(fl_res, fl_res_2)
                                        # else it is a long rage neighbor
                                        else:
                                            nn.add_long(fl_res, fl_res_2)
                                    # if it is not in the same chain it is an inter chain neighbor
                                    else:
                                        nn.add_inter(fl_res, fl_res_2)
                                        already_have.append(res.get_full_id())

        return nn
Ejemplo n.º 25
0
def is_H_bond_old(atom_A, atom_D):
    """
    CG -
    acceptor:atom1
    donors:atom2
    source RDOCK
    X-A - - - D-Y
    is Hbond if:
    dist (A-D) <3.5
    100<angle(XAD)<180
    60<angle(YDA)<120
    """

    if atom_A.get_parent() != atom_D.get_parent():
        NS = NeighborSearch(
            [atom for atom in atom_A.get_parent() if atom_A != atom])
        is_hbond = False
        for atom_X in NS.search(center=atom_A.get_coord(),
                                radius=parametres.cutoff_bonds):
            angle = calcul_angle(atom_X.get_coord(), atom_A.get_coord(),
                                 atom_D.get_coord())
            angle = min(angle, 360 - angle)
            if 100 < angle < 180:
                is_hbond = True
                break

        if is_hbond:
            NS = NeighborSearch(
                [atom for atom in atom_D.get_parent() if atom_D != atom])
            is_hbond = False
            for atom_Y in NS.search(center=atom_D.get_coord(),
                                    radius=parametres.cutoff_bonds):
                angle = calcul_angle(atom_Y.get_coord(), atom_D.get_coord(),
                                     atom_A.get_coord())
                angle = min(angle, 360 - angle)
                if 60 < angle < 120:
                    is_hbond = True
                    break
            if is_hbond:
                return True

    return False
    def extract_feature(self):
        seed(self.seed)
        print_info_nn(
            " >>> Adding D1 surface shape distribution for database {0} ... ".
            format(self._database.name))
        overall_time = datetime.now()
        counter = 0
        if not os.path.exists(self._get_dir_name()):
            os.makedirs(self._get_dir_name())
        for complex_name in self._database.complexes.keys():
            protein_complex = self._database.complexes[complex_name]
            proteins = [
                protein_complex.unbound_formation.ligand,
                protein_complex.unbound_formation.receptor
            ]
            for protein in proteins:
                shape_dist_file = self._get_dir_name() + protein.name
                if not os.path.exists(shape_dist_file + ".npy"):
                    counter += 1
                    if counter <= 15:
                        print_info_nn("{0}, ".format(protein.name))
                    else:
                        counter = 0
                        print_info("{0}".format(protein.name))
                    atoms = protein.atoms
                    neighbour_search = NeighborSearch(atoms)
                    distributions = np.zeros(
                        (len(protein.residues), self.number_of_bins + 1))
                    for i in range(len(protein.residues)):
                        residue = protein.residues[i]
                        nearby_residues = [protein.biopython_residues[i]]
                        temp_nearby_residues = neighbour_search.search(
                            residue.center, self.radius, "R")
                        for nearby_residue in temp_nearby_residues:
                            if nearby_residue not in protein.biopython_residues:
                                continue
                            residues_index = protein.biopython_residues.index(
                                nearby_residue)
                            residue = protein.residues[residues_index]

                            if residue.get_feature(
                                    Features.RELATIVE_ACCESSIBLE_SURFACE_AREA
                            ) >= self.rASA_threshold:
                                nearby_residues.append(nearby_residue)
                        distributions[i, :] = self._compute_distribution(
                            nearby_residues, residue.center)
                    np.save(shape_dist_file, distributions)
                distributions = np.load(shape_dist_file + ".npy")
                for i in range(len(protein.residues)):
                    protein.residues[i].add_feature(
                        Features.D1_SURFACE_SHAPE_DISTRIBUTION,
                        distributions[i, :])
        print_info("took {0} seconds.".format(
            (datetime.now() - overall_time).seconds))
Ejemplo n.º 27
0
    def set_contacts(self):
        """
            Fill in the contact list
            self.contacts = [(id residue 1, id residue 2), (id residue 1,
            id residue 2), (id residue 1, id residue 2), ...].
            All those contacts will be search in available DBs.
        """
        model0_atoms = self.chain.get_atoms()
        atoms_pairs = NeighborSearch(list(model0_atoms)).search_all(16.4)

        for atom_pair in atoms_pairs:
            at1 = atom_pair[0]
            at2 = atom_pair[1]
            chain1 = at1.parent.parent.id
            chain2 = at2.parent.parent.id
            if chain1 != chain2:
                continue
            res_name1 = at1.parent.get_resname().rstrip().lstrip()
            res_name2 = at2.parent.get_resname().rstrip().lstrip()
            atm_name1 = at1.get_fullname().rstrip().lstrip()
            atm_name2 = at2.get_fullname().rstrip().lstrip()
            res_id1 = at1.parent.get_id()[1]  # res number
            res_id2 = at2.parent.get_id()[1]  # res number
            if res_id1 == res_id2:
                continue
            if (res_id1 == res_id2 + 3) or (res_id2 == res_id1 + 3):
                continue
            if self.check_neighborhood(res_id1, res_id2) != 6:
                continue
            if not self.has_neighborhood(res_id1) or \
                    not self.has_neighborhood(res_id2):
                continue
            if res_name1 in RESIDUELIST and res_name2 in RESIDUELIST and \
               atm_name1 == 'CA' and atm_name2 == 'CA':
                dstc = distance.euclidean(at1.coord, at2.coord)
                if 3.35 <= dstc <= 16.4:
                    if res_id1 < res_id2 and (res_id1, res_id2) \
                       not in self.contacts:
                        self.contacts.append((res_id1, res_id2))
                    elif res_id2 < res_id1 and (res_id2, res_id1) \
                            not in self.contacts:
                        self.contacts.append((res_id2, res_id1))
                    else:
                        continue

        if len(self.residues_in_ray) > 0:
            # print len(self.contacts)
            tmp = [
                j for j in self.contacts if j[0] in self.residues_in_ray
                and j[1] in self.residues_in_ray
            ]
            self.contacts = tmp
            # print len(self.contacts)
            '''for i, res_ctt in enumerate(self.contacts):
Ejemplo n.º 28
0
def secondary_struc_cmap(chain,
                         sequence,
                         structure,
                         cutoff_distance=4.5,
                         cutoff_numcontacts=10,
                         exclude_neighbour=3,
                         ss_elements=['H', 'E', 'B', 'b', 'G']):

    atom_list = Selection.unfold_entities(chain, 'A')
    res_list = Selection.unfold_entities(chain, 'R')

    res_names, numbering = [], []
    for res in res_list:
        res_names.append(res.get_resname())
        numbering.append(res.get_id()[1])

    numbering = np.array(numbering)
    res_range = np.array(range(len(numbering)))

    assert len(structure) == len(
        numbering
    ), f'PDB file and Secondary structure map do not match!\n {chain.get_parent().get_parent().id} - PDB: {len(res_list)} Residues VS. STRIDE: {len(sequence)} Residues. '

    ns = NeighborSearch(atom_list)
    all_neighbours = ns.search_all(cutoff_distance, 'A')

    struc_length = len(structure)
    segment = np.zeros([struc_length], dtype='int')
    nseg = 1
    for i in range(struc_length):
        if structure[i] in ss_elements:
            segment[i] = nseg
            if i == struc_length:
                nseg += 1
            elif structure[i + 1] != structure[i]:
                nseg += 1
    nseg -= 1

    index_list = []
    for atompair in all_neighbours:
        res1 = res_range[numbering == atompair[0].get_parent().id[1]][0]
        res2 = res_range[numbering == atompair[1].get_parent().id[1]][0]

        if abs(res1 - res2) > exclude_neighbour:
            if segment[res1] != 0 and segment[res2] != 0 and segment[
                    res1] != segment[res2]:
                index_list.append((segment[res1] - 1, segment[res2] - 1))

    index_list.sort()
    count = Counter(index_list)
    index = [values for values in count if count[values] >= cutoff_numcontacts]

    return np.array(index), segment
Ejemplo n.º 29
0
def check_clash(model, chain_to_add, clash_distance=2.5):
    """
    Checks wether a newly added chain has clashes with the rest of the structure. Returns a set containing the clashing chains and a boolean indicating whether the newly added chain is clashing with itself or not.
    model: previous structure.
    chain_to_add: new chain (Chain object from PDB.Chain).
    clash_distance: indicates a distance threshold (in Angstroms) to consider two atoms as clashing.
    """

    # Initialization of NeighbourSearch, that allows to find clashes
    neighbor_object = NeighborSearch(list(model.get_atoms()))

    structure_clashing_chains = set()
    total_clashes = 0

    # For each atom, clashes are compute
    for atom in chain_to_add.get_atoms():
        clashes = neighbor_object.search(atom.get_coord(), clash_distance)

        if len(clashes) > 0:  # If clashes are found...

            # Increase the total number of clashes and add the conflicting chains to the set
            for clash in clashes:
                structure_clashing_chains.add(
                    clash.get_parent().get_parent().id)
                total_clashes += 1

    # In case the new chain is conflicting with several chains
    if len(structure_clashing_chains) > 1 and total_clashes > 20:
        return structure_clashing_chains, False

    elif len(structure_clashing_chains
             ) == 1 and total_clashes > 20 and chain_to_add.id[1] == list(
                 structure_clashing_chains)[0][1]:

        clash_chain = model[0][list(structure_clashing_chains)
                               [0]]  # Conflictive chain
        RMSD = superimpose(clash_chain, chain_to_add)  # Compute RMSD

        # If the RMSD is lower than 3.0, the chain is clashing with itself.
        if RMSD <= 3.0:
            return structure_clashing_chains, True

        # Else the chain is clashing with another chain of the structure
        else:
            return structure_clashing_chains, False

    elif total_clashes > 20:
        return structure_clashing_chains, False

    # No clashes found
    else:
        return None, False
Ejemplo n.º 30
0
    def check_if_collide(self, component, point, radius):
        """
        check whether aparticulat point does not collide with any components atoms
        
        Return all component's atoms that have at least one
        atom within radius of center for given point
        """
        ns = NeighborSearch(list(component.get_atoms()))
        point_center = array([point.x, point.y, point.z])
        #we assume that pseudoresidue radius ;lis 1.5A as a collistion detection area.
        found_collisions = len(ns.search(point_center, radius + 1.5, "A"))

        return found_collisions