Boost logo

Boost :

From: Gennadiy Rozental (gennadiy.rozental_at_[hidden])
Date: 2004-11-16 16:05:18

> using the library primitives inside the "apply" function. After all,
> why not make "apply" a free function?
> template <class Params>
> void apply(Params& p, Whatever x) {
> // use p's "passive" interface to operate on x
> }

This looks like good idea, but as it is you couldn't put it into library,
since you don't know which interface to use to operate on x. What you could
do is to make above function to apply all params to x

template <class Params>
void apply(Params& p, Whatever x) {
    for_each<Param>( do_apply_to(x) );

and user will be required to write do_apply functions:

void do_apply( name_param, A& a ) {
        a.m_name = name_param.value;

void do_apply( suffix_param, A& a ) {
        a.m_name.append( name_param.value );

void do_apply( prefix_param, A& a ) {
        a.m_name.prepend( name_param.value );

> > Hmm. Well, I did not find it nor in docs. Why IMO it's most
> > important part of functionality. I see it now in test. Why did you
> > name function f_list? Why not just f as rest of them?
> Where are you seeing f_list?

In your test program.

> > I meant "within brackets". My problem is that it's p[name | "abc"] while
> > would prefer something like p[name] | "abc".
> That's not doable in general. Suppose the argument was an int? What
> is
> p[index] | 3
> ??

Yeah,. I's not possible. But within brackets is not very good
either IMO

> > It's just an interface I would prefer.
> If we provide the interface you requested, to query whether a value
> is supplied, then you could have your "explicit interface" too. It's
> a little verbose for my tastes, but to each his own I guess.

> > It could. I did that.
> Please show how the library can help with the "active" part. The
> passive library can be used to build an active component easily
> enough. I just don't see how the library can help with the apply
> call.

Yes. User will be required to implement all apply calls for all parameters.
Note though:

1. "Passive" solution does require the same: one need to 'apply' (assign)
named parameter value to the target at the point of usage (not in the
2. In case of "active" solution you actually do it once and then could reuse
it for many different functions

class Entry {

class Logger {
      log( msg, Params p )
           Entry e( msg );
           p.apply_to( e );


      buffer( msg, Params p )
           m_entries.push_back( Entry( msg ) );
           p.apply_to( m_entries.back() );

      buffer( multichunk_msg, Params p )
           m_entries.push_back( Entry( multichunk_msg ) );
           p.apply_to( m_entries.back() );

    vector<Entry> m_entries;

> >> Because we looked at the use cases; the major example we could find
> >> was the Boost.Graph library, which is a library of function
> >> templates. We thought it would be bad if the library didn't work
> >> for function templates.
> >
> > Sorry I am not familiar with that example. Could you please give more
> > details on what exactly is wrong wit strict type checking?
> If you have a templated function parameter that you want to be able to
> name, you can't require that it is one particular type.
> template <class T>
> void f(T x); // what strict type is T?

Sorry. I still not sure I understand. Let me put it as following example:

template<typename T>
void log( std::string prefix, std::string name, std::string separ, T const&
v )
     std::cout << prefix << name << separ << v;

template<typename Params>
log( Params const& p )
      log( p[prefix | "" ], p[name], p[separator | " = " ], p[value] );

Yeah. In this case keyword "value" couldn't be typed. Ok. I slightly
reworked my code see attached. Now it supports both typed and non-typed
keywords. all in 120 lines (I am sure it could be made smaller by more
effective mpl use). I also eliminated "keyword coupling". Now it should be
as good in this regard as submitted library.

> >> > This library instead invented special mechanism of imposing
> >> > restrictions.
> >>
> >> Not really; it used a de-facto standard approach for passing
> >> compile-time functions.
> >
> > Yeah. But in C++ de-facto standard approach for enforcing parameters
> > types is to specify one.
> Unless you're writing a function template.

If you have named template parameter it should be non-typed. In other case
it should be typed.

> > I do not know about python, but in c++ I prefer named interface
> > wouldn't break by switching order of parameter specification.
> What do you mean by "break?" When parameter names are used there is
> no restriction on parameter order.
> f(arg1, arg2, arg3, key5 = arg5, key6 = arg6, key4 = arg4)
> ^^^^^^^^^^^^^^^^ ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
> positional position-independent.

Let consider an example of two optional parameters name, value. Then

foo( "abc", value = 5 ) works
foo( value = 5 ) works
foo( value = 5, "abc" ) doesn't work.

> These two are related; it should be clear from what I've written
> above. Your code can allow at most one of these (I didn't check):
> either it allows unchecked types and there's no ability to control
> overload resolution, or it doesn't support function templates with
> keyword arguments. And unless you have some way to induce SFINAE,
> you have no way to distinguish multiple overloads of the same
> function name accepting different named parameter sets:
> int foo1( c_str name, float v, int i )
> {
> }
> int foo2( int id )

But you sad "multiple overloads of the same function"
Above should look like
int foo1( int id )
> {
> }
> template<class Params>
> int foo(Params const& params)
> {
> foo1( params[name], params[value], params[index] );
> }
> template<class Params>
> int foo(Params const& params) // error, foo already defined.
> {
> foo2( params[id] );
> }

We don't need two. I would write:

template<class Params>
int foo(Params const& params)
    if( name and value present )
       foo1( params[name], params[value], params[index] );
       foo1( params[index] );

> >> and with the problem of keyword coupling (because of the integer
> >
> > What do you mean by coupling? That we need to supply unique integer
> > id?
> Yes. You can't develop keywords independently.

I do not see to many differences from your solution. You also need unique id
for the keyword, which you then organize in ordered structure. So
essentially getting the same result.

> Yeah, but you don't need PS to cause ETI and other issues on VC <= 7.0

Do we still care? Enough to affect the design/implementation?

> > I wouldn't be using it. Why would I use canon to kill sparrow.
> Why would anyone kill a sparrow?!! ;-)

It's just Russian saying I was trying to translate. Don't know English

> Dave Abrahams


begin 666 b.cpp
M/&)O;W-T+VUP;"]D97)E9BYH<' ^"B-I;F-L=61E(#QB;V]S="]M<&PO9FEN
M9%]I9BYH<' ^"B-I;F-L=61E(#QB;V]S="]M<&PO;&ES="YH<' ^"B-I;F-L
M/'1Y<&5N86UE($Y0,2QT>7!E;F%M92!.4#(^(" @(" @<W1R=6-T(&YA;65D
M871E/'1Y<&5N86UE('5N:7%U95]I9#X@(" @(" @(" @(" @<W1R=6-T(&ME
M9#X*<W1R=6-T(&AA<U]I9 I["B @("!T96UP;&%T93QT>7!E;F%M92!.4#X*
M(" @('-T<G5C="!A<'!L>0H@(" @>PH@(" @(" @('1Y<&5D968@='EP96YA
M;64_at_8F]O<W0Z.FES7W-A;64\='EP96YA;64_at_3E Z.FED+$ED/CHZ='EP92!T
M>7!E.PH@(" @?3L*?3L*"G1E;7!L871E/'1Y<&5N86UE(%!A<F%M5'EP97,L
M='EP96YA;64_at_260^"G-T<G5C="!T>7!E7V]F7VYP( I["B @('1Y<&5D968@
M='EP96YA;64@;7!L.CIF:6YD7VEF/%!A<F%M5'EP97,L:&%S7VED/$ED/B ^
M"B @("!T96UP;&%T93QT>7!E;F%M92!.4#X*(" @(&YA;65D7W!A<F%M971E
M<E]C;VUB:6YE/$Y0+$1E<FEV960^"B @("!O<&5R871O<BPH($Y0(&-O;G-T
M)B!N<" I"B @("!["B @(" @(" @<F5T=7)N(&YA;65D7W!A<F%M971E<E]C
M/BAT:&ES*2 I.PH@(" @?0I].PH*=&5M<&QA=&4\='EP96YA;64_at_5"P@='EP
M9#X@/@I["B @("!T>7!E9&5F(%0@(" @(" @(" @(" @(" @(" @(" @(" @
M(" @(" @(" @(" @(" @(&1A=&%?='EP93L*(" @('1Y<&5D968@;7!L.CIL
M93L*(" @('1Y<&5D968@=6YI<75E7VED(" @(" @(" @(" @(" @(" @(" @
M(" @(" @(" @(" @:60["@H@(" @;F%M961?<&%R86UE=&5R*"!4(&-O;G-T
M)B!V("D_at_.B!M7W9A;'5E*"!V("D@>WT*"B @("!4(&-O;G-T)B!O<&5R871O
M<FX@;5]V86QU93L@?0H*(" @(%0_at_8V]N<W0F(&U?=F%L=64["GT["@IT96UP
M;&%T93QT>7!E;F%M92!R97-?='EP93X*<W1R=6-T(&%C8V5S<U]F:7)S= I[
M"B @("!T96UP;&%T93QT>7!E;F%M92!.4#$L='EP96YA;64_at_3E R+'1Y<&5N
M86UE($M7/@H@(" @<W1A=&EC(')E<U]T>7!E(&-O;G-T)B!?*"!.4#$@8V]N
M<W0F(&YP,2P_at_3E R(&-O;G-T)B!N<#(L($M7(&-O;G-T)B!K=R I('L@<F5T
M/@IS=')U8W0_at_86-C97-S7W)E<W0*>PH@(" @=&5M<&QA=&4\='EP96YA;64@
M3E Q+'1Y<&5N86UE($Y0,BQT>7!E;F%M92!+5SX*(" @('-T871I8R!R97-?
M='EP92!C;VYS="8_at_7R@@3E Q(&-O;G-T)B!N<#$L($Y0,B!C;VYS="8@;G R
M;&%T93QT>7!E;F%M92!.4#$L='EP96YA;64_at_3E R/@IS=')U8W0@;F%M961?
M9%]P87)A;65T97)?8V]M8FEN93Q.4#$L3E R/B ^"GL*(" @('1Y<&5D968@
M;F%M92!.4#(Z.G!A<F%M7W1Y<&4^('!A<F%M7W1Y<&4["@H@(" @;F%M961?
M<&%R86UE=&5R7V-O;6)I;F4H($Y0,2!C;VYS="8@;G Q+"!.4#(@8V]N<W0F
M(&YP,B I"B @(" Z(&U?;G Q*"!N<#$@*2P@;5]N<#(H(&YP,B I"B @("![
M?0H*(" @('1E;7!L871E/'1Y<&5N86UE($M7/@H@(" @='EP96YA;64@='EP
M<W0F( H@(" @;W!E<F%T;W);72@@2U<@8V]N<W0F(&MW("D_at_8V]N<W0*(" @
M('L@"B @(" @("!T>7!E9&5F('1Y<&5N86UE('1Y<&5?;V9?;G \<&%R86U?
M='EP92QT>7!E;F%M92!+5SHZ:60^.CIT>7!E(')E<U]T>7!E.PH@(" @(" @
M;F%M92!+5SHZ:60L='EP96YA;64_at_3E Q.CII9#XL"B @(" @(" @("!A8V-E
M<W-?9FER<W0\<F5S7W1Y<&4^+&%C8V5S<U]R97-T/')E<U]T>7!E/B ^.CIT
M>7!E(&%C8V5S<V]R.PH@"B @(" @("!R971U<FX_at_86-C97-S;W(Z.E\H(&U?
M;G Q+"!M7VYP,BP@:W<@*3L*(" @('T*"B @("!.4#$@8V]N<W0F(&U?;G Q
M.PH@(" @3E R(&-O;G-T)B!M7VYP,CL*?3L*"G1E;7!L871E/'1Y<&5N86UE
M('5N:7%U95]I9#X*<W1R=6-T(&ME>7=O<F0*>PH@(" @='EP961E9B!U;FEQ
M=65?:60@:60["@H@(" @=&5M<&QA=&4\='EP96YA;64_at_5#X*(" @(&YA;65D
M7W!A<F%M971E<CQ4+'5N:7%U95]I9#X*(" @(&]P97)A=&]R/2@@5"!C;VYS
M="8@=" I(&-O;G-T"B @("!["B @(" @(" @<F5T=7)N(&YA;65D7W!A<F%M
M971E<CQ4+'5N:7%U95]I9#XH('0@*3L*(" @('T*?3L*"G1E;7!L871E/'1Y
M>7=O<F0_at_.B!K97EW;W)D/'5N:7%U95]I9#X*>PH@(" @;F%M961?<&%R86UE
M=&5R/%0L=6YI<75E7VED/@H@(" @;W!E<F%T;W(]*"!4(&-O;G-T)B!T("D@
M8V]N<W0*(" @('L*(" @(" @("!R971U<FX@;F%M961?<&%R86UE=&5R/%0L
M=6YI<75E7VED/B@@=" I.PH@(" @?0I].PH*+R\O+R\O+R\O+R\O+R\O+R\O
M=#X@(" @(" @(&EN9&5X.PH@(&ME>7=O<F0\<W1R=6-T('9A;'5E7W0^(" @
M(" @(" @(" @(" @(" @=F%L=64["@H@('1E;7!L871E/'1Y<&5N86UE(%9A
M=BP@:6YT(&D@*0H@('L*(" @(" @<W1D.CIC;W5T(#P\(&X@/#P@)ULG(#P\
M(&D@/#P@(ET](B \/"!V(#P\('-T9#HZ96YD;#L*("!]"@H@('1E;7!L871E
M*0H@('L*(" @(" @9F]O*"!P87)A;7-;;F%M95TL('!A<F%M<UMV86QU95TL
M9R!T97-T.CIF;V\["B @('5S:6YG('1E<W0Z.FYA;64["B @('5S:6YG('1E
M<W0Z.G9A;'5E.PH@("!U<VEN9R!T97-T.CII;F1E>#L*"B @(&9O;R_at_H(&EN
M9&5X(#T@,"P@;F%M92 ](")F;V\B+"!V86QU92 ](#(N-2 I*3L*(" @9F]O
M*"@@:6YD97@@/2 Q+"!N86UE(#T@(F9O;R(L('9A;'5E(#T@)V$G("DI.PH@
M("!F;V\H*"!I;F1E>" ](#(L(&YA;64@/2 B9&]O(BP@=F%L=64@/2 B86)C
7(B I*3L*"@H@("!R971U<FX@,#L*?0H`

Boost list run by bdawes at, gregod at, cpdaniel at, john at