WIP factored out another helper, not yet tested...
This commit is contained in:
parent
bb390f2ef1
commit
c8c577c4cc
2 changed files with 85 additions and 8 deletions
|
|
@ -692,6 +692,46 @@ namespace func {
|
|||
|
||||
|
||||
|
||||
/**
|
||||
* Bind a specific argument to an arbitrary value.
|
||||
* Especially, this "value" might be another binder.
|
||||
*/
|
||||
template<typename SIG, typename X, uint n>
|
||||
class BindToArgument
|
||||
{
|
||||
typedef typename _Fun<SIG>::Args Args;
|
||||
typedef typename _Fun<SIG>::Ret Ret;
|
||||
typedef typename Args::List ArgsList;
|
||||
typedef typename Types<X>::List ValList;
|
||||
|
||||
enum { ARG_CNT = count<ArgsList>::value };
|
||||
|
||||
typedef typename Splice<ArgsList, ValList, n>::Front RemainingFront;
|
||||
typedef typename Splice<ArgsList, ValList, n>::Back RemainingBack;
|
||||
typedef typename func::PlaceholderTuple<RemainingFront>::PlaceholderSeq::List PlaceholdersBefore;
|
||||
typedef typename func::PlaceholderTuple<RemainingBack,n>::PlaceholderSeq::List PlaceholdersBehind;
|
||||
typedef typename Append<typename Append<PlaceholdersBefore,ValList>::List
|
||||
,PlaceholdersBehind
|
||||
>::List PreparedArgs;
|
||||
typedef typename Append<RemainingFront, RemainingBack>::List ReducedArgs;
|
||||
|
||||
typedef tuple::BuildTuple<PreparedArgs, ValList, n> BuildPreparedArgs;
|
||||
typedef typename Tuple<LeftReplaced>::TupleType PreparedArgTuple;
|
||||
|
||||
|
||||
public:
|
||||
typedef function<typename FunctionTypedef<Ret,ReducedArgs>::Sig> ReducedFunc;
|
||||
|
||||
static ReducedFunc
|
||||
reduced (SIG& f, Tuple<ValList> const& val)
|
||||
{
|
||||
PreparedArgTuple params (BuildPreparedArgs::create(val));
|
||||
return func::Apply<ARG_CNT>::template bind<ReducedFunc> (f, params);
|
||||
}
|
||||
};
|
||||
|
||||
|
||||
|
||||
namespace { // ...helpers for specifying types in function declarations....
|
||||
|
||||
template<typename RET, typename ARG>
|
||||
|
|
@ -798,16 +838,18 @@ namespace func {
|
|||
return PApply<SIG,ArgTypeSeq>::bindFront (f, val);
|
||||
}
|
||||
|
||||
/** close the given function over the last argument */
|
||||
template<typename SIG, typename ARG>
|
||||
|
||||
/** bind the last function argument to an arbitrary term,
|
||||
* which especially might be a (nested) binder... */
|
||||
template<typename SIG, typename TERM>
|
||||
typename _PapE<SIG>::Function
|
||||
applyLast (SIG& f, ARG arg)
|
||||
bindLast (SIG& f, TERM arg)
|
||||
{
|
||||
typedef typename _PapE<SIG>::Arg ArgType;
|
||||
typedef Types<ArgType> ArgTypeSeq;
|
||||
typedef Tuple<ArgTypeSeq> ArgTuple;
|
||||
ArgTuple val(arg);
|
||||
return PApply<SIG,ArgTypeSeq>::bindBack (f, val);
|
||||
typedef Types<TERM> ArgTypeSeq;
|
||||
typedef Tuple<ArgTypeSeq> ArgTuple;
|
||||
ArgTuple argT(arg);
|
||||
const int LAST_POS = count<typename _Fun<SIG>::Args>::value;
|
||||
return BindToArgument<SIG,TERM,LAST_POS>::reduced (f, argT);
|
||||
}
|
||||
|
||||
|
||||
|
|
|
|||
|
|
@ -135,6 +135,7 @@ namespace test {
|
|||
check_diagnostics ();
|
||||
check_partialApplication ();
|
||||
check_functionalComposition ();
|
||||
check_bindToArbitraryParameter ();
|
||||
}
|
||||
|
||||
|
||||
|
|
@ -315,6 +316,40 @@ namespace test {
|
|||
ASSERT (1+2+3+4+5 == func::chained(f5, ff) (_1_,_2_,_3_,_4_,_5_) );
|
||||
}
|
||||
|
||||
|
||||
|
||||
void
|
||||
check_bindToArbitraryParameter ()
|
||||
{
|
||||
typedef Num<1> Sig15(Num<1>,Num<2>,Num<3>,Num<4>,Num<5>);
|
||||
typedef Num<1> SigR1( Num<2>,Num<3>,Num<4>,Num<5>);
|
||||
typedef Num<1> SigR2(Num<1>, Num<3>,Num<4>,Num<5>);
|
||||
typedef Num<1> SigR3(Num<1>,Num<2>, Num<4>,Num<5>);
|
||||
typedef Num<1> SigR4(Num<1>,Num<2>,Num<3>, Num<5>);
|
||||
typedef Num<1> SigR5(Num<1>,Num<2>,Num<3>,Num<4> );
|
||||
|
||||
typedef Num<5> SigI5(Num<5>);
|
||||
|
||||
Sig15& f = fun15<1,2,3,4,5>;
|
||||
SigI5& f5 = fun11<5>;
|
||||
Tuple<Types<char> > argT(55);
|
||||
|
||||
SigR1& f_red1 = BindToArgument<Sig15,char,0>::reduced (f, argT);
|
||||
SigR2& f_red2 = BindToArgument<Sig15,char,1>::reduced (f, argT);
|
||||
SigR3& f_red3 = BindToArgument<Sig15,char,2>::reduced (f, argT);
|
||||
SigR4& f_red4 = BindToArgument<Sig15,char,3>::reduced (f, argT);
|
||||
SigR5& f_red5 = BindToArgument<Sig15,char,4>::reduced (f, argT);
|
||||
|
||||
ASSERT (55+2+3+4+5 == f_red1 ( _2_,_3_,_4_,_5_) );
|
||||
ASSERT (1+55+3+4+5 == f_red1 (_1_, _3_,_4_,_5_) );
|
||||
ASSERT (1+2+55+4+5 == f_red1 (_1_,_2_, _4_,_5_) );
|
||||
ASSERT (1+2+3+55+5 == f_red1 (_1_,_2_,_3_, _5_) );
|
||||
ASSERT (1+2+3+4+55 == f_red1 (_1_,_2_,_3_,_4_ ) );
|
||||
|
||||
SigR5& f_2bind = bindLast (f, bind(f5, Num<5>(99)));
|
||||
ASSERT (1+2+3+4+99 == f_2bind (_1_,_2_,_3_,_4_ ) );
|
||||
}
|
||||
|
||||
};
|
||||
|
||||
|
||||
|
|
|
|||
Loading…
Reference in a new issue