Boost logo

Boost Users :

From: Patrick Mézard (pmezard_at_[hidden])
Date: 2005-03-03 03:12:12


Gennadiy Rozental <gennadiy.rozental <at> thomson.com> writes:

> You have several choices
>
> 1. You could define operator<< in namespace foo

It does not work because of the typedef (see below). Please see my first answer
to Vladimir. It works if it is defined in namespace std:: however.

> 2. You could use BOOST_TEST_DONT_PRINT_LOG_VALUE(your type) on global scope
> to prevent values of this type being printed at all

Okay, but since I am the one writing the tests, I would simply use BOOST_CHECK().

> 3. You could write struct C2 : foo::C {}; And unless you use non-default
> constructor it will work.

Maybe, but it seems much more work just to use BOOST_CHECK_EQUAL().

I could understand the anonymous namespace and typedefs have issues with ADL and
there are workaround to be found. For those interested with ADL rules, I finally
got an old post from llewely on comp.lang.c+.moderated on a similar problem
stating that (look for "Re: stream iterators and operator<< " in google.groups):

<quote>
A typedef name is not a type. The occurance of a typedef name in a
    scope does not add that scope to consideration in
    argument-dependent lookup. [3.4.2/2]

Unqualified lookup does not occur because inside the definition of the
    function called by '*it = *v.begin()', operator<< is used for a
    function call. Instead, argument-dependent lookup is
    used. [3.4.2/1]

Argument dependent lookup will lookup names in the classes and
    namespaces associated with the argument types. pair<int,int> is a
    template-id, and defined at namespace scope in namespace std, with
    arguments int,int, which have no associated namespaces or classes,
    so the only associated namespace is std. [3.4.2/2, bullet 8]

I believe both compilers are conforming in this respect.

Some notes: If you move the operator<< into namespace std, it will be
    found during argument-dependent lookup (I tested with gcc
    3.2.1), except for the caveat that one is not allowed to add
    overloads to namespace std. If you change 'typedef pair<int,int> Type'
    to 'typedef pair<int,Foo>', where Foo is in the global namespace,
    the operator<< will also be found.
</quote>

Personnaly, I would stick with declaring the operator<< in std:: for the moment.
That's ugly but that's just tests after all. Maybe you could just add a
documentation note on this topic.

Thank you for your answer.

Patrick Mézard.


Boost-users list run by williamkempf at hotmail.com, kalb at libertysoft.com, bjorn.karlsson at readsoft.com, gregod at cs.rpi.edu, wekempf at cox.net