Closed davidbrochart closed 3 years ago
The first commit implemented a partial dispatch which supported only 1 argument on which to dispatch and 1 argument on which not to dispatch ("ignored argument"). This second commit supports an arbitrary number of arguments on which to dispatch and 1 ignored argument.
I'm wondering if it's possible to have the partial dispatcher not separate from the normal dispatcher, with an optional ignored argument.
It's actually possible and I think it's the way to go.Let's illustrate this with the basic_fast_dispatcher
, the reasoning is similar with the basic_dispatcher
. The idea is to add a template parameter for the non dispatched arguments after the return_type
parameter:
template
<
class type_list,
class return_type,
class undispatched_type_list
class callback_type
>
class basic_fast_dispatcher;
and define the specialization for mpl::vector
only:
template
<
class return_type,
class callback_type,
class... B,
class... T,
>
class basic_fast_dispatcher<mpl::vector<B...>, return_type, mpl::vector<T...>, callback_type>
{
// Implementation very similar to the existing one except that you forward the non dispatched arguments
inline return_type dispatch(B&... args, T&... udargs) const
{
index_type index = {{args.get_class_index()...}};
return dispatch_impl<0>(m_callbacks, index, args..., udargs...);
}
};
The template parameter for non dispatched type is also added to the functor_dispatcher, and is defaulted to the empty mpl::vector
:
template
<
class type_list,
class return_type,
class undispatched_type = mpl::vector<>,
template <class, class> class casting_policy = dynamic_caster,
template <class, class, class> class dispatcher = basic_dispatcher
>
class functor_dispatcher;
template
<
class return_type,
template <class, class> class casting_policy,
template <class, class, class> class dispatcher,
class... B,
class... T
>
class functor_dispatcher<mpl::vector<B...>, return_type, mpl::vector<T...>, casting_policy, dispatcher>
{
// Similar implementation except that you forward the additional arguments without casting them:
template <class... D, class Fun>
void insert(const Fun& fun)
{
functor_type f([fun](B&... args, T&... targs) -> return_type
{
return fun(casting_policy<D&, B&>::cast(args)..., targs...);
});
m_backend.template insert<D...>(std::move(f));
}
inline return_type dispatch(B&... args, T&... targs) const
{
return m_backend.dispatch(args..., targs);
}
};
Thanks @JohanMabille. It's still annoying to have to set a default parameter (for which you want the default value) when you want to set a parameter that is further in the list. Maybe @serge-sans-paille could use his C++ fu to do something similar to params14 for template parameters :smile:
Awesome!
Checklist
Description