1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112
|
#define CATCH_CONFIG_MAIN // This tells Catch to provide a main() - only do
// this in one cpp file
#include "catch.hpp"
#include <GraphMol/RDKitBase.h>
#include <GraphMol/SmilesParse/SmilesParse.h>
#include <GraphMol/SmilesParse/SmilesWrite.h>
using namespace RDKit;
TEST_CASE("Github #1972", "[SMILES,bug]") {
SECTION("basics") {
std::vector<std::vector<std::string>> smiles = {
{"[C@@]1(Cl)(F)(I).Br1", "[C@@](Br)(Cl)(F)(I)"},
{"[C@@](Cl)(F)(I)1.Br1", "[C@@](Cl)(F)(I)Br"},
{"[C@@](Cl)1(F)(I).Br1", "[C@@](Cl)(Br)(F)(I)"},
{"[C@@](Cl)(F)1(I).Br1", "[C@@](Cl)(F)(Br)(I)"}};
for (const auto &pr : smiles) {
std::unique_ptr<ROMol> m1(SmilesToMol(pr[0]));
std::unique_ptr<ROMol> m2(SmilesToMol(pr[1]));
REQUIRE(m1);
REQUIRE(m2);
auto csmi1 = MolToSmiles(*m1);
auto csmi2 = MolToSmiles(*m2);
CHECK(csmi1 == csmi2);
}
}
SECTION("further examples") {
std::vector<std::vector<std::string>> smiles = {
{"[C@@]1(Cl)2(I).Br1.F2", "[C@@](Br)(Cl)(F)(I)"},
{"[C@@](Cl)2(I)1.Br1.F2", "[C@@](Cl)(F)(I)Br"},
{"[C@@]12(Cl)(I).Br1.F2", "[C@@](Br)(F)(Cl)(I)"},
{"[C@@]21(Cl)(I).Br1.F2", "[C@@](F)(Br)(Cl)(I)"},
{"[C@@](Cl)12(I).Br1.F2", "[C@@](Cl)(Br)(F)(I)"},
{"[C@@](Cl)21(I).Br1.F2", "[C@@](Cl)(F)(Br)(I)"},
{"[C@@](Cl)(I)21.Br1.F2", "[C@@](Cl)(I)(F)(Br)"},
{"[C@@](Cl)(I)12.Br1.F2", "[C@@](Cl)(I)(Br)(F)"}};
for (const auto &pr : smiles) {
std::unique_ptr<ROMol> m1(SmilesToMol(pr[0]));
std::unique_ptr<ROMol> m2(SmilesToMol(pr[1]));
REQUIRE(m1);
REQUIRE(m2);
auto csmi1 = MolToSmiles(*m1);
auto csmi2 = MolToSmiles(*m2);
CHECK(csmi1 == csmi2);
}
}
}
TEST_CASE("Github #2029", "[SMILES,bug]") {
SECTION("wedging") {
std::unique_ptr<ROMol> m1(SmilesToMol("CN[C@H](Cl)C(=O)O"));
REQUIRE(m1);
m1->getBondWithIdx(1)->setBondDir(Bond::BEGINWEDGE);
bool doKekule = false, allBondsExplicit = false;
CHECK("" == SmilesWrite::GetBondSmiles(m1->getBondWithIdx(1), -1, doKekule,
allBondsExplicit));
allBondsExplicit = true;
CHECK("-" == SmilesWrite::GetBondSmiles(m1->getBondWithIdx(1), -1, doKekule,
allBondsExplicit));
}
SECTION("direction") {
std::unique_ptr<ROMol> m1(SmilesToMol("C/C=C/C"));
REQUIRE(m1);
bool doKekule = false, allBondsExplicit = false;
CHECK("" == SmilesWrite::GetBondSmiles(m1->getBondWithIdx(0), -1, doKekule,
allBondsExplicit));
CHECK("" == SmilesWrite::GetBondSmiles(m1->getBondWithIdx(2), -1, doKekule,
allBondsExplicit));
allBondsExplicit = true;
CHECK("/" == SmilesWrite::GetBondSmiles(m1->getBondWithIdx(0), -1, doKekule,
allBondsExplicit));
CHECK("/" == SmilesWrite::GetBondSmiles(m1->getBondWithIdx(2), -1, doKekule,
allBondsExplicit));
}
SECTION("aromatic double bonds") {
std::unique_ptr<RWMol> m1(SmilesToMol("c1ccccc1"));
REQUIRE(m1);
bool markAtomsBonds = false;
MolOps::Kekulize(*m1, markAtomsBonds);
bool doKekule = false, allBondsExplicit = false;
CHECK("" == SmilesWrite::GetBondSmiles(m1->getBondWithIdx(0), -1, doKekule,
allBondsExplicit));
CHECK("" == SmilesWrite::GetBondSmiles(m1->getBondWithIdx(1), -1, doKekule,
allBondsExplicit));
allBondsExplicit = true;
CHECK("=" == SmilesWrite::GetBondSmiles(m1->getBondWithIdx(0), -1, doKekule,
allBondsExplicit));
CHECK("-" == SmilesWrite::GetBondSmiles(m1->getBondWithIdx(1), -1, doKekule,
allBondsExplicit));
}
}
TEST_CASE("Smiles literals", "[SMILES]") {
auto mol = "c1ccccc1"_smiles;
REQUIRE(mol);
CHECK(6 == mol->getNumAtoms());
auto fail1 = "c1ccccc"_smiles;
REQUIRE(!fail1);
auto fail2 = "c1cccn1"_smiles;
REQUIRE(!fail2);
}
TEST_CASE("Smarts literals", "[Smarts]") {
auto mol = "c1ccc[c,n]c1"_smarts;
REQUIRE(mol);
CHECK(6 == mol->getNumAtoms());
auto fail1 = "c1ccccc"_smarts;
REQUIRE(!fail1);
auto mol2 = "c1cccn1"_smarts;
REQUIRE(mol2);
}
|