Commit 123d25f8 by Maarten L. Hekkelman

formatting of floating points in cif files

better verbose info for differences
parent 7f820449
...@@ -2,6 +2,7 @@ Version 3.0.0 ...@@ -2,6 +2,7 @@ Version 3.0.0
- Replaced many strings in the API with string_view for - Replaced many strings in the API with string_view for
performance reasons. performance reasons.
- Upgraded mmcif::Structure - Upgraded mmcif::Structure
- various other small fixes
Version 2.0.4 Version 2.0.4
- Reverted a too strict test when reading cif files. - Reverted a too strict test when reading cif files.
......
...@@ -36,8 +36,11 @@ ...@@ -36,8 +36,11 @@
#include <regex> #include <regex>
#include <set> #include <set>
#include <sstream> #include <sstream>
#include <iomanip>
#include <shared_mutex> #include <shared_mutex>
#include <boost/format.hpp>
#include "cif++/CifUtils.hpp" #include "cif++/CifUtils.hpp"
/* /*
...@@ -142,6 +145,19 @@ class Item ...@@ -142,6 +145,19 @@ class Item
public: public:
Item() {} Item() {}
Item(std::string_view name, char value)
: mName(name)
, mValue({ value })
{
}
template<typename T, std::enable_if_t<std::is_floating_point_v<T>, int> = 0>
Item(std::string_view name, const T& value, const char *fmt)
: mName(name)
, mValue((boost::format(fmt) % value).str())
{
}
template <typename T, std::enable_if_t<std::is_arithmetic_v<T>, int> = 0> template <typename T, std::enable_if_t<std::is_arithmetic_v<T>, int> = 0>
Item(const std::string_view name, const T &value) Item(const std::string_view name, const T &value)
: mName(name) : mName(name)
......
...@@ -137,6 +137,22 @@ class DSSP ...@@ -137,6 +137,22 @@ class DSSP
public: public:
friend class iterator; friend class iterator;
ResidueInfo()
: mImpl(nullptr)
{
}
ResidueInfo(const ResidueInfo &rhs)
: mImpl(rhs.mImpl)
{
}
ResidueInfo& operator=(const ResidueInfo &rhs)
{
mImpl = rhs.mImpl;
return *this;
}
explicit operator bool() const { return not empty(); } explicit operator bool() const { return not empty(); }
bool empty() const { return mImpl == nullptr; } bool empty() const { return mImpl == nullptr; }
......
...@@ -604,6 +604,8 @@ void Datablock::write(std::ostream &os, const std::vector<std::string> &order) ...@@ -604,6 +604,8 @@ void Datablock::write(std::ostream &os, const std::vector<std::string> &order)
bool operator==(const cif::Datablock &dbA, const cif::Datablock &dbB) bool operator==(const cif::Datablock &dbA, const cif::Datablock &dbB)
{ {
bool result = true;
std::shared_lock lockA(dbA.mLock); std::shared_lock lockA(dbA.mLock);
std::shared_lock lockB(dbB.mLock); std::shared_lock lockB(dbB.mLock);
...@@ -632,14 +634,59 @@ bool operator==(const cif::Datablock &dbA, const cif::Datablock &dbB) ...@@ -632,14 +634,59 @@ bool operator==(const cif::Datablock &dbA, const cif::Datablock &dbB)
while (catA_i != catA.end() and catB_i != catB.end()) while (catA_i != catA.end() and catB_i != catB.end())
{ {
if (not iequals(*catA_i, *catB_i)) std::string nA = *catA_i;
return false; ba::to_lower(nA);
std::string nB = *catB_i;
ba::to_lower(nB);
int d = nA.compare(nB);
if (d > 0)
{
auto cat = dbB.get(*catB_i);
if (cat == nullptr)
missingA.push_back(*catB_i);
++catB_i;
}
else if (d < 0)
{
auto cat = dbA.get(*catA_i);
if (cat == nullptr)
missingB.push_back(*catA_i);
++catA_i;
}
else
++catA_i, ++catB_i; ++catA_i, ++catB_i;
} }
if (catA_i != catA.end() or catB_i != catB.end()) while (catA_i != catA.end())
missingB.push_back(*catA_i++);
while (catB_i != catB.end())
missingA.push_back(*catB_i++);
if (not (missingA.empty() and missingB.empty()))
{
if (cif::VERBOSE > 1)
{
std::cerr << "compare of datablocks failed" << std::endl;
if (not missingA.empty())
std::cerr << "Categories missing in A: " << ba::join(missingA, ", ") << std::endl
<< std::endl;
if (not missingB.empty())
std::cerr << "Categories missing in B: " << ba::join(missingB, ", ") << std::endl
<< std::endl;
result = false;
}
else
return false; return false;
}
// Second loop, now compare category values // Second loop, now compare category values
catA_i = catA.begin(), catB_i = catB.begin(); catA_i = catA.begin(), catB_i = catB.begin();
...@@ -660,13 +707,21 @@ bool operator==(const cif::Datablock &dbA, const cif::Datablock &dbB) ...@@ -660,13 +707,21 @@ bool operator==(const cif::Datablock &dbA, const cif::Datablock &dbB)
else else
{ {
if (not (*dbA.get(*catA_i) == *dbB.get(*catB_i))) if (not (*dbA.get(*catA_i) == *dbB.get(*catB_i)))
{
if (cif::VERBOSE > 1)
{
std::cerr << "Compare of datablocks failed due to unequal values in category " << *catA_i << std::endl;
result = false;
}
else
return false; return false;
}
++catA_i; ++catA_i;
++catB_i; ++catB_i;
} }
} }
return true; return result;
} }
std::ostream& operator<<(std::ostream &os, const Datablock &data) std::ostream& operator<<(std::ostream &os, const Datablock &data)
...@@ -2355,6 +2410,8 @@ bool operator==(const Category &a, const Category &b) ...@@ -2355,6 +2410,8 @@ bool operator==(const Category &a, const Category &b)
{ {
using namespace std::placeholders; using namespace std::placeholders;
bool result = true;
// set<std::string> tagsA(a.fields()), tagsB(b.fields()); // set<std::string> tagsA(a.fields()), tagsB(b.fields());
// //
// if (tagsA != tagsB) // if (tagsA != tagsB)
...@@ -2388,7 +2445,7 @@ bool operator==(const Category &a, const Category &b) ...@@ -2388,7 +2445,7 @@ bool operator==(const Category &a, const Category &b)
// a.reorderByIndex(); // a.reorderByIndex();
// b.reorderByIndex(); // b.reorderByIndex();
auto rowEqual = [&](const cif::Row& a, const cif::Row& b) auto rowEqual = [&](const cif::Row& ra, const cif::Row& rb)
{ {
int d = 0; int d = 0;
...@@ -2399,11 +2456,15 @@ bool operator==(const Category &a, const Category &b) ...@@ -2399,11 +2456,15 @@ bool operator==(const Category &a, const Category &b)
std::tie(tag, compare) = tags[kix]; std::tie(tag, compare) = tags[kix];
d = compare(a[tag].c_str(), b[tag].c_str()); d = compare(ra[tag].c_str(), rb[tag].c_str());
if (d != 0) if (d != 0)
{
if (cif::VERBOSE > 1)
std::cerr << "Values in _" << a.name() << '.' << tag << " are not equal: '" << ra[tag].c_str() << "' != '" << rb[tag].c_str() << '\'' << std::endl;
break; break;
} }
}
return d == 0; return d == 0;
}; };
...@@ -2412,12 +2473,26 @@ bool operator==(const Category &a, const Category &b) ...@@ -2412,12 +2473,26 @@ bool operator==(const Category &a, const Category &b)
while (ai != a.end() or bi != b.end()) while (ai != a.end() or bi != b.end())
{ {
if (ai == a.end() or bi == b.end()) if (ai == a.end() or bi == b.end())
{
if (cif::VERBOSE > 1)
{
std::cerr << "Unequal number of rows in " << a.name() << std::endl;
result = false;
break;
}
else
return false; return false;
}
cif::Row ra = *ai, rb = *bi; cif::Row ra = *ai, rb = *bi;
if (not rowEqual(ra, rb)) if (not rowEqual(ra, rb))
{
if (cif::VERBOSE > 1)
result = false;
else
return false; return false;
}
std::vector<std::string> missingA, missingB, different; std::vector<std::string> missingA, missingB, different;
...@@ -2434,14 +2509,22 @@ bool operator==(const Category &a, const Category &b) ...@@ -2434,14 +2509,22 @@ bool operator==(const Category &a, const Category &b)
const char* tb = rb[tag].c_str(); if (strcmp(tb, ".") == 0 or strcmp(tb, "?") == 0) tb = ""; const char* tb = rb[tag].c_str(); if (strcmp(tb, ".") == 0 or strcmp(tb, "?") == 0) tb = "";
if (compare(ta, tb) != 0) if (compare(ta, tb) != 0)
{
if (cif::VERBOSE > 1)
{
std::cerr << "Values in _" << a.name() << '.' << tag << " are not equal: '" << ta << "' != '" << tb << '\'' << std::endl;
result = false;
}
else
return false; return false;
} }
}
++ai; ++ai;
++bi; ++bi;
} }
return true; return result;
} }
// auto Category::iterator::operator++() -> iterator& // auto Category::iterator::operator++() -> iterator&
......
...@@ -897,7 +897,6 @@ void CalculateBetaSheets(std::vector<Res>& inResidues, DSSP_Statistics& stats) ...@@ -897,7 +897,6 @@ void CalculateBetaSheets(std::vector<Res>& inResidues, DSSP_Statistics& stats)
} }
// -------------------------------------------------------------------- // --------------------------------------------------------------------
// TODO: improve alpha helix calculation by better recognizing pi-helices
void CalculateAlphaHelices(std::vector<Res>& inResidues, DSSP_Statistics& stats, bool inPreferPiHelices = true) void CalculateAlphaHelices(std::vector<Res>& inResidues, DSSP_Statistics& stats, bool inPreferPiHelices = true)
{ {
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment