Boost logo

Boost :

Subject: Re: [boost] [type_traits] is_complete<T> possible realization
From: Matt Calabrese (rivorus_at_[hidden])
Date: 2012-11-09 12:18:41


On Fri, Nov 9, 2012 at 9:38 AM, Antony Polukhin <antoshkka_at_[hidden]> wrote:

> You can always add some more misc template parameters:
>

No, you can't. You always have the same exact problem if you just add more
template parameters, only you're hiding it more. That said, I'm not as
convinced that this type of metafunction is impossible, it's just that your
current approach cannot be made to succeed. I believe you should be able to
create the metafunction without directly violating ODR if you encode the
checking process into the evaluation of a default template argument, or if
you use template aliases. This works because the evaluation of the
condition happens at the time the parameters are passed (not inside of the
template), meaning that you don't have to worry about memoization, and
since the result is a template argument, you don't violate ODR either (at
least not directly). Testing this approach yields promising results in
clang and gcc: http://codepaste.net/xfgcu8

The linked code works fine in Clang 3.1 and GCC 4.7, with C++11 support on.
I believe that you can even hide the default parameter through the use of a
template alias and still technically avoid memoization, but while Clang
seems to agree with me on that, GCC does not.

There is an caveat, though. While I believe this gets around ODR directly,
you still have to be careful when using it, as would be the case for any
kind of completeness checker. Consider the type of ODR problem in the
following:

// Begin Translation Unit A
struct foo;

template< class T >
struct your_code
{
  // Do something valid when the type is incomplete
};
// End Tranlation Unit A

// Begin Translation Unit B
struct foo {};

template< class T >
struct your_code
{
  // Do something valid when the type is complete
};
// End Tranlation Unit B

//////////

While the above code might seem contrived, it could definitely happen when
dealing with forward declarations of classes. Because of this, I'd
recommend in general only using a completeness checker with something like
a static_assert anyway, forcing compilation to fail when you don't get the
result that you'd expect, otherwise you have to be extremely careful.

-- 
-Matt Calabrese

Boost list run by bdawes at acm.org, gregod at cs.rpi.edu, cpdaniel at pacbell.net, john at johnmaddock.co.uk