$include_dir="/home/hyper-archives/boost/include"; include("$include_dir/msg-header.inc") ?>
From: Tobias Schwinger (tschwinger_at_[hidden])
Date: 2005-06-19 18:32:11
David Abrahams wrote:
> Tobias Schwinger <tschwinger_at_[hidden]> writes:
> 
> 
>>Hi Dave,
>>
>>
>>David Abrahams wrote:
>>
>>>I can only explain the reasons I chose a reference and not a pointer
>>>in the context of Boost.Python: pointers can be null, but references
>>>cannot, and you can never call a member function on a null pointer.
>>>
>>
>>We have to start a "bit further above" ;-).
> 
> 
> I don't know what you mean.
>
It was referring to the next sentence. "Rewinding" the discussion to one thought 
before the above part of your post...
> 
>>If we want to unify parameters and class type we have to either use a reference 
>>or a pointer to it for things to make sense.
> 
> 
> Yes.
> 
> 
>>The by-value case (operator() member of a simple functor) is too unusual to make 
>>sense in general.
> 
> 
> Not sure what you mean here.  I don't think there's any case in which
> a member function can reasonably have the target object passed by
> value.
> 
I'm not entirely sure there is, either. We agree enough, here.
> 
>>I also agree, that a reference is the more reasonable default.
>>
>>Further, it is attractive to have a reference (as opposed to a value) in the 
>>sequence because (e.g):
>>
>>     // Let t be a variable of type T and some
>>     // T be some (member) function pointer/reference type
>>     function< typename function_type<plain_function,T>::type > x = t;
>>     //        ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
>>     // "rebinds" the subtypes of T to a plain_function
>>
>>will just work.
> 
> 
> Right.
> 
> 
>>I still don't think it is good to hard-wire this, though.
> 
> 
> Why?
> 
> 
>>If I understand your case correctly, you want remove const qualification of the 
>>class type (which are not there, currently - but planned):
>>
>>     typename add_reference
>>     < typename remove_cv
>>        < typename remove_reference
>>           < typename function_type_class<T>::type
>>             // or typename at_c<sig,1>::type
>>           >::type
>>        >::type
>>     >::type
> 
> 
> Yes, but I don't really think this library should make any special
> allowances for my weird case.  Boost.Python may not be able to use
> this library anyway because of the need for vc6/7 compatibility, but
> if it can, I'll strip the cv-qualification myself.
> 
The next is not /that/ unusual (at least I've seen it in several places in Boost)...
> 
>>Slightly better for those who want a pointer:
>>
>>     typename add_pointer
>>     < typename remove_reference
>>       < typename function_type_class<T>::type
>>         // or typename at_c<sig,1>::type
>>       >::type
>>     >::type
>>
>>So I believe it is perhaps best to parametrize the decoartion we want on the 
>>class type:
> 
> 
> I disagree.  Too much parameterization is an impediment to usability.
This is only a good argument if no parametrization provides better usability, I 
guess ;-).
And we'll set reference decoration as the default (see further below) so you 
only see it if we want something else.
> 
> [BTW, so is the endline layout you're using for nested templates.
> There's little precedent for it anywhere that I've seen.  You wouldn't
> write
> 
>    foo
>    ( bar
>      ( baz(1)
>      )
>    );
> 
> would you?]
> 
Did you mean:
      __attribute__(__whatever__) foooooooooooooooooooooo
      ( __attribute__(__whatever__) baaaaaaaaaaaaaaaaaaaaaaar
        ( __attribute__(__whatever__) baaaaaaaaaaaaaaaaaaaaaaaaaz
        ).get_something()
      ).get_something()
;-) ? I sure would!
> 
>>Sidenote: I'm not entirely sure on the MPL-Lamda expression
> 
  ^ in the following section
> 
> Your posting didn't show one above, although I can guess what the example
> you would have written would look like.
> 
> 
>>- we could also use 
>>some kind of tag type or an enum, I guess. Or we use MPL-Lambda exressions, but 
>>only evaluate them as a fallback when there is no optimized specialization, as 
>>for add_reference<_>, add_pointer<_> and identity<_> (maybe even one to create 
>>an unqualified reference for the Boost.Python case). Thoughts welcome.
>>
>>     template<typename T, typename ClassDecoration = add_reference<_> >
>>     struct function_type_signature;
>>
>>     template<typename T, typename ClassDecoration = add_reference<_> >
>>     struct function_type_class;
>>
>>And if we want to add a unified one:
>>
>>     template<typename T, typename ClassDecoartion = add_reference<_> >
>>     struct function_type_effective_parameters;
>>
>>(Jonathan Turkanis has suggested adding one like this. He also came up with 
>>"effective" for the name, which I happen to like).
> 
> 
> Remind me again why you're still using the function_type_ prefix?
Because it hasn't been changed in documentation and the library, yet (so it's 
easier to follow our discussion) and 'class' conflicts with a keyword.
> 
> 
>>And perhaps even:
>>
>>     template<typename Tag, typename TypeOrTypes,
>>              typename ClassDecoartion = add_reference<_> >
>>     struct function_type;
>>     // ignores it, unless it specializes function_type_signature
> 
>                   ^^         ^^
>                   what are these?  Are they the same "it?"
Whoops, sorry!
I had to re-read it three times to make any sense of it, myself.
And on second though the semantics I meant are no good.
Please, just ignore it.
> 
>>Revisiting the example from above we could say:
>>
>>     function< typename function_type<plain_function,T,add_pointer<_> >::type >
>>
>>And easily even use our favourite proxy, e.g. a smart pointer...
> 
> 
> Now that you bring that case up, parameterization starts to look a bit
> more attractive.  I'm still leary of going in that direction, though.
Did you think about iterating the sequences...
Thanks,
Tobias