示例#1
0
bool StripSmallFragments(RWMol &mol, bool verbose) {
  const bool sanitize=false;
  std::vector<boost::shared_ptr<ROMol> > frags = MolOps::getMolFrags(mol, sanitize);
  if (frags.size() <= 1)
    return false;

  size_t maxFragSize = 0;
  size_t maxFragIdx = 0;
  
  for(size_t i=0; i<frags.size(); ++i) {
    const unsigned int fragSize = frags[i].get()->getNumAtoms();
    if(fragSize >= maxFragSize) {
      maxFragSize = fragSize;
      maxFragIdx = i;
    }
  }

  if(verbose) {
    std::string name = "<no name>";
    mol.getPropIfPresent(common_properties::_Name, name);
    for(size_t i=0; i<frags.size(); ++i) {
      if (i != maxFragIdx) {
        BOOST_LOG(rdWarningLog) << name << " removed fragment i="<<i<<" with "
            << frags[i].get()->getNumAtoms() << " atoms" << std::endl;
      }
    }

  }

  // we need to save chirality for checking later
  bool checkChiral = false;
  if(mol.hasProp(RDKit::common_properties::_MolFileChiralFlag)) {
    unsigned int chiralflag = mol.getProp<unsigned int>(
        RDKit::common_properties::_MolFileChiralFlag);
    frags[maxFragIdx].get()->setProp<unsigned int>(
        RDKit::common_properties::_MolFileChiralFlag, chiralflag);
    checkChiral = chiralflag != 0;
  }
     
  mol = *frags[maxFragIdx].get();

  // We need to see if the mol file's chirality possibly came from this
  //  fragment.
  if (checkChiral) {
    bool ischiral = false;
    
    RWMol copy(mol);
    try {
      MolOps::sanitizeMol(copy);
      ClearSingleBondDirFlags(copy);
      const Conformer &conf = copy.getConformer();
      DetectBondStereoChemistry(copy, &conf);
      MolOps::assignStereochemistry(copy, true, true, true);
      for (ROMol::AtomIterator atIt =copy.beginAtoms(); atIt != copy.endAtoms();
           ++atIt) {
        if((*atIt)->hasProp(common_properties::_ChiralityPossible)) {
          ischiral = true;
          checkChiral = false;
          break;
        }
      }
    } catch (...) {
    }

    // are chiral tags set
    if(checkChiral) {
      for (ROMol::AtomIterator atIt = mol.beginAtoms(); atIt != mol.endAtoms();
           ++atIt) {
        if ( (*atIt)->getChiralTag() == Atom::CHI_TETRAHEDRAL_CW ||
             (*atIt)->getChiralTag() == Atom::CHI_TETRAHEDRAL_CCW ) {
          ischiral = true;
          break;
        }
      }
      
      for (ROMol::BondIterator bondIt = mol.beginBonds(); bondIt != mol.endBonds();
           ++bondIt) {
        if ((*bondIt)->getBondDir() == Bond::BEGINDASH ||
            (*bondIt)->getBondDir() == Bond::BEGINWEDGE) {
          ischiral = true;
          break;
        }
      }
    }
    
    if (!ischiral) {
      mol.setProp<unsigned int>(RDKit::common_properties::_MolFileChiralFlag, 0);
    }
  }
  return true;
}
  // ------------------------------------------------------------------
  //
  // Enumerates the library around a template and returns the result.
  //
  //
  // ------------------------------------------------------------------
  RWMOL_SPTR_VECT enumerateLibrary(RWMol *templateMol,
				   VECT_RWMOL_SPTR_VECT &sidechains,
				   bool orientSidechains){
    PRECONDITION(templateMol,"bad molecule");
    RWMOL_SPTR_VECT res,tmp;
    res.push_back(RWMOL_SPTR(new RWMol(*templateMol)));

    // if there's no attachment point on the molecule or no
    // sidechains, return now: 
    if(!templateMol->hasProp(common_properties::maxAttachIdx) || sidechains.size()==0 )
      return res;

    int maxIdx;
    templateMol->getProp(common_properties::maxAttachIdx,maxIdx);

    tmp.clear();
    // loop over the sidechains and attach them
    for(unsigned int i=0;i<sidechains.size();i++){
      int tgtMark=CONNECT_BOOKMARK_START+i;
      // here's another boundary condition
      if(tgtMark>maxIdx) break;

      /// loop over all atoms with the appropriate mark
      //  This means that if a mol has two attachment points with the
      //  same name (e.g. two Xa's) they'll always have the same
      //  sidechain attached to them.  This is a feature.
      RWMOL_SPTR_VECT::iterator sidechainIt;
      for(sidechainIt=sidechains[i].begin();
	  sidechainIt!=sidechains[i].end();
	  sidechainIt++){
	// we've got our sidechain, find the atom it attaches from
	if( (*sidechainIt)->hasAtomBookmark(CONNECT_BOOKMARK_START) ){
	  //
	  // NOTE: If there's more than one marked atom in the sidechain,
	  ///      we'll only use the first for the moment.
	  //
	  int sidechainAtomIdx = (*sidechainIt)->getAtomWithBookmark(CONNECT_BOOKMARK_START)->getIdx();
	
	  // now add the sidechain to each molecule
	  RWMOL_SPTR_VECT::iterator templMolIt;
	  // loop over all the mols we've generated to this point
	  for(templMolIt=res.begin();templMolIt!=res.end();templMolIt++){
	    RWMol *templ =  new RWMol(**templMolIt);
	    std::string name,tmpStr;
	    if(templ->hasProp(common_properties::_Name)){
	      templ->getProp(common_properties::_Name,tmpStr);
	      name = name + " " + tmpStr;
	    }
	    while(templ->hasAtomBookmark(tgtMark)){
	      // this is the atom we'll be replacing in the template
	      Atom *at = templ->getAtomWithBookmark(tgtMark);

	      // copy and transform the sidechain:
	      RWMol *sidechain;
	      if(orientSidechains){
		sidechain = new RWMol(*(sidechainIt->get()));
		orientSidechain(templ,sidechain,
				at->getIdx(),sidechainAtomIdx);
	      } else {
		sidechain = sidechainIt->get();
	      }
	      // FIX: need to use the actual bond order here:
	      molAddSidechain(templ,sidechain,
			      at->getIdx(),sidechainAtomIdx,
			      Bond::SINGLE);
	      if(sidechain->hasProp(common_properties::_Name)){
		sidechain->getProp(common_properties::_Name,tmpStr);
		name = name + " " + tmpStr;
	      }
	      templ->clearAtomBookmark(tgtMark,at);
	      if(orientSidechains){
		delete sidechain;
	      }
	    }
	    //std::cout << templ << "> " << MolToSmiles(*templ) << std::endl;
	    if(name != "") templ->setProp(common_properties::_Name,name);
	    tmp.push_back(RWMOL_SPTR(templ));
	  }
	}
      }

      //
      // if we just made any molecules, free up the memory used by the
      // existing result set and move the molecules we just generated
      // over
      if(tmp.size()){
#if 0      
	RWMOL_SPTR_VECT::iterator tmpMolIt;
	for(tmpMolIt=res.begin();tmpMolIt!=res.end();tmpMolIt++){
	  delete *tmpMolIt;
	}
#endif
	res = tmp;
	tmp.clear();
      }
    }
    return res;
  }