Another C++ Unit Testing Idea

In a previous blog entry about unit-testing in C++ I wrote that instead of writing something like this...
expected = 42;
actual = expression();
assert_equals(expected, actual);
you could write something like this...
ARE_EQUAL(int)
{
    ...
    expected = 42;
    actual = 40+1
}
Admittedly this was not much of an improvement, if at all. However, on a flight to Oslo a few days ago I suddenly realized a way to improve it. The idea is to fold an expected == actual assertion down to this:
expected(42) == actual(40+1);
Where expected and actual can be two function templates that return objects wrapping their arguments. These objects can have an overloaded == operator that does the assertion for me. Instead of emphasizing the assertion I emphasize the roles instead. Here's some proof of concept code:
#include <cassert>
#include <iostream>

template<typename T>
struct asserted_role
{
   asserted_role(const char * name, const T * ptr)
       : name(name)
       , ptr(ptr)
   {
   }
   const char * name;
   const T * ptr;
};

template<typename T>
void failed_assertion(const asserted_role<T> & lhs,
               const char * op,
               const asserted_role<T> & rhs)
{ 
   std::cout << "FAILED ASSERTION" ...   
       << " " << lhs.name << "(" << *lhs.ptr << ") " 
       << op 
       << " " << rhs.name << "(" << *rhs.ptr << ")" 
       << endl;      
}

template<typename T>
void operator==(const asserted_role<T> & lhs,
         const asserted_role<T> & rhs)
{
   if (*lhs.ptr == *rhs.ptr)
       ;
   else
      failed_assertion(lhs, "==", rhs);
}

template<typename T>
asserted_role<T> expected(const T & t)
{
   return asserted_role<T>("expected", &t);
}

template<typename T>
asserted_role<T> actual(const T & t)
{
   return asserted_role<T>("actual", &t);
}

int main()
{
   expected(42) == actual(40+1);
}
There are a couple of things I like about this idea. The first is I no longer have to remember to get the expected and actual in the right order; if I want to I can write:
   actual(40+1) == expected(42);
The second is that the idea can be extended. For example, I can create similar function templates called lesser and greater and add a < operator:
   lesser(42) < greater(40+1);
I can create a new template function of any name I like to express the role I'm thinking of. For example, suppose I want to test that the value of one expression is equal to the value of another expression, but neither value is "expected" or "actual" they are just two values and I don't care what the values actually are, other than the two values are equal. I can create two function templates called lhs and rhs:
   lhs(2 + 2) == rhs(4);