[/
 / Copyright (c) 2008 Eric Niebler
 /
 / Distributed under the Boost Software License, Version 1.0. (See accompanying
 / file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
 /]

[section:implementation Appendix D: Implementation Notes]

[section:sfinae Quick-n-Dirty Type Categorization]

Much has already been written about dispatching on type traits using
SFINAE (Substitution Failure Is Not An Error) techniques in C++. There
is a Boost library, Boost.Enable_if, to make the technique idiomatic.
Proto dispatches on type traits extensively, but it doesn't use
`enable_if<>` very often. Rather, it dispatches based on the presence
or absence of nested types, often typedefs for void.

Consider the implementation of `is_expr<>`. It could have been written
as something like this:

    template<typename T>
    struct is_expr
      : is_base_and_derived<proto::some_expr_base, T>
    {};

Rather, it is implemented as this:

    template<typename T, typename Void = void>
    struct is_expr
      : mpl::false_
    {};

    template<typename T>
    struct is_expr<T, typename T::proto_is_expr_>
      : mpl::true_
    {};

This relies on the fact that the specialization will be preferred
if `T` has a nested `proto_is_expr_` that is a typedef for `void`.
All Proto expression types have such a nested typedef.

Why does Proto do it this way? The reason is because, after running
extensive benchmarks while trying to improve compile times, I have
found that this approach compiles faster. It requires exactly one
template instantiation. The other approach requires at least 2:
`is_expr<>` and `is_base_and_derived<>`, plus whatever templates
`is_base_and_derived<>` may instantiate.

[endsect]

[section:function_arity Detecting the Arity of Function Objects]

In several places, Proto needs to know whether or not a function
object `Fun` can be called with certain parameters and take a
fallback action if not. This happens in _callable_context_ and
in the _call_ transform. How does Proto know? It involves some
tricky metaprogramming. Here's how.

Another way of framing the question is by trying to implement
the following `can_be_called<>` Boolean metafunction, which
checks to see if a function object `Fun` can be called with
parameters of type `A` and `B`:

    template<typename Fun, typename A, typename B>
    struct can_be_called;

First, we define the following `dont_care` struct, which has an
implicit conversion from anything. And not just any implicit
conversion; it has a ellipsis conversion, which is the worst possible
conversion for the purposes of overload resolution:

    struct dont_care
    {
        dont_care(...);
    };

We also need some private type known only to us with an overloaded
comma operator (!), and some functions that detect the presence of
this type and return types with different sizes, as follows:

    struct private_type
    {
        private_type const &operator,(int) const;
    };

    typedef char yes_type;      // sizeof(yes_type) == 1
    typedef char (&no_type)[2]; // sizeof(no_type)  == 2

    template<typename T>
    no_type is_private_type(T const &);

    yes_type is_private_type(private_type const &);

Next, we implement a binary function object wrapper with a very
strange conversion operator, whose meaning will become clear later.

    template<typename Fun>
    struct funwrap2 : Fun
    {
        funwrap2();
        typedef private_type const &(*pointer_to_function)(dont_care, dont_care);
        operator pointer_to_function() const;
    };

With all of these bits and pieces, we can implement `can_be_called<>` as
follows:

    template<typename Fun, typename A, typename B>
    struct can_be_called
    {
        static funwrap2<Fun> &fun;
        static A &a;
        static B &b;

        static bool const value = (
            sizeof(no_type) == sizeof(is_private_type( (fun(a,b), 0) ))
        );

        typedef mpl::bool_<value> type;
    };

The idea is to make it so that `fun(a,b)` will always compile by adding
our own binary function overload, but doing it in such a way that we can
detect whether our overload was selected or not. And we rig it so that
our overload is selected if there is really no better option. What follows
is a description of how `can_be_called<>` works.

We wrap `Fun` in a type that has an implicit conversion to a pointer to
a binary function. An object `fun` of class type can be invoked as
`fun(a, b)` if it has such a conversion operator, but since it involves
a user-defined conversion operator, it is less preferred than an
overloaded `operator()`, which requires no such conversion.

The function pointer can accept any two arguments by virtue
of the `dont_care` type. The conversion sequence for each argument is
guaranteed to be the worst possible conversion sequence: an implicit
conversion through an ellipsis, and a user-defined conversion to
`dont_care`. In total, it means that `funwrap2<Fun>()(a, b)` will
always compile, but it will select our overload only if there really is
no better option.

If there is a better option --- for example if `Fun` has an overloaded
function call operator such as `void operator()(A a, B b)` --- then
`fun(a, b)` will resolve to that one instead. The question now is how
to detect which function got picked by overload resolution.

Notice how `fun(a, b)` appears in `can_be_called<>`: `(fun(a, b), 0)`.
Why do we use the comma operator there? The reason is because we are
using this expression as the argument to a function. If the return type
of `fun(a, b)` is `void`, it cannot legally be used as an argument to
a function. The comma operator sidesteps the issue.

This should also make plain the purpose of the overloaded comma operator
in `private_type`. The return type of the pointer to function is
`private_type`. If overload resolution selects our overload, then the
type of `(fun(a, b), 0)` is `private_type`. Otherwise, it is `int`.
That fact is used to dispatch to either overload of `is_private_type()`,
which encodes its answer in the size of its return type.

That's how it works with binary functions. Now repeat the above process
for functions up to some predefined function arity, and you're done.

[endsect]

[/
    [section:ppmp_vs_tmp Avoiding Template Instiations With The Preprocessor]

    TODO

    [endsect]
]

[endsect]
