BOOST_CHECK_EQUAL with pair<int, int> and custom operator <<
boost, boost-test, c++
Solution
Putting `operator<<` in `std` like Remus's answer is undefined behavior in the C++ 14 draft (N4296 section:17.6.4.2.1). Boost provides a hook (used by this answer) and you can write:
namespace boost
{
namespace test_tools
{
template<typename T,typename U>
struct print_log_value<std::pair<T, U> >
{
void operator()(std::ostream& os, std::pair<T, U> const& pr)
{
os << "<" << std::get<0>(pr) << "," << std::get<1>(pr) << ">";
}
};
}
}
`print_log_value` is a template so if you are not declaring a templated value like `pair<T,U>`, you will need to write something like:
template<>
struct print_log_value<MyType>{ /* implementation here*/ };
Edit
If you are using boost 1.59 or later you need to use namespace `boost::test_tools::tt_detail` instead. That is, the code needs to start:
namespace boost
{
namespace test_tools
{
namespace tt_detail
{
Problem
When attempting to do a BOOST_CHECK_EQUAL(pair, pair), gcc doesnt find the stream operator for pair, inspite of declaring it. The funny thing is that std::out finds the operator. ``` ostream& operator<<(ostream& s, const pair<int,int>& p) { s << '<' << p.first << ',' << p.second << '>'; return s; } BOOST_AUTO_TEST_CASE(works) { pair<int,int> expected(5, 5); pair<int,int> actual (5, 5); std::cout << expected << std::endl; std::cout << actual << std::endl; BOOST_CHECK(actual == expected); } BOOST_AUTO_TEST_CASE(no_work) { pair<int,int> expected(5, 5); pair<int,int> actual (5, 5); BOOST_CHECK_EQUAL(actual, expected); } ``` This doesnt compile with the error: ``` ... instantiated from here ../boost-atp/release/include/boost/test/test_tools.hpp:326:9: error: no match for ‘operator<<’ in ‘ostr << t’ ```