Skip to content

Instantly share code, notes, and snippets.

@tclamb
Last active December 9, 2015 21:06
Show Gist options
  • Save tclamb/9149587 to your computer and use it in GitHub Desktop.
Save tclamb/9149587 to your computer and use it in GitHub Desktop.
minimal working implementation of catch-lib's CHECK
#include <iostream>
struct is_unary
{
operator bool() { return {}; };
};
template <typename lhsT, typename rhsT>
struct result
{
lhsT lhs_val;
rhsT rhs_val;
bool passed;
result(lhsT l, rhsT r, bool p) : lhs_val{l}, rhs_val{r}, passed{p} {};
bool binary = true;
result<lhsT, rhsT> done() {
return *this;
}
};
template <typename lhsT>
struct result<lhsT, is_unary>
{
lhsT lhs_val;
is_unary rhs_val;
bool passed;
result(lhsT l, is_unary, bool p) : lhs_val{l}, passed{p} {};
bool binary = false;
};
template <typename lhsT>
struct result_builder
{
lhsT lhs_val;
result_builder(lhsT l) : lhs_val{l} {};
#define BIN_OPS X(==) \
X(!=) \
X(< ) \
X(<=) \
X(> ) \
X(>=)
#define X(bin_op) template<typename rhsT> \
result<lhsT, rhsT const&> operator bin_op (rhsT const& rhs_val) { \
return {lhs_val, rhs_val, lhs_val bin_op rhs_val}; \
}
BIN_OPS
#undef X
#undef BIN_OPS
/*
template<typename rhsT>
result<lhsT, rhsT const&> operator==(rhsT const& expr) {
return {lhs_val, expr, lhs_val == expr};
}
*/
result<lhsT, is_unary> done() {
return {lhs_val, is_unary{}, static_cast<bool>(lhs_val)};
}
};
struct lhs
{
template<typename T>
result_builder<T const&> operator<= (T const& expr) {
return {expr};
}
};
#define CHECK(expr) do { \
auto res = (lhs{}<=expr).done(); \
if (!res.passed) { \
std::cerr << "check failed: " #expr "\n"; \
if (res.binary) { \
std::cerr << " expanded: " << res.lhs_val << " == " << res.rhs_val << "\n"; \
} else { \
std::cerr << " expanded: " << res.lhs_val << "\n"; \
} \
} \
} while(0)
int main() {
auto zero = [](){ return 0; };
auto one = [](){ return 1; };
CHECK(zero() == one());
CHECK(zero());
CHECK(one());
CHECK(one() == 1);
CHECK(one() != 1);
CHECK(zero() > one());
CHECK(zero() <= one());
auto counter = [x=0]() mutable { return x++; }
CHECK(counter() == zero());
CHECK(counter() == one());
CHECK(counter() == one());
return 0;
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment