Boost logo

Boost :

Subject: Re: [boost] [local_function] any interest in a LocalFunction library?
From: Lorenzo Caminiti (lorcaminiti_at_[hidden])
Date: 2010-08-31 13:23:20


On Fri, Aug 27, 2010 at 1:39 PM, Pierre Morcello
<pmorcell-cppfrance_at_[hidden]> wrote:
> Lorenzo Caminiti wrote :
>> I got a first version of Boost.LocalFunction implemented.
>
> 1/
> Sorry, I think I just realized I told you something wrong earlier on the list. One year ago, interest was raised towards unnamed local fonction. I missed that you were aiming for named function. we did not discuss named local function.

Do you have a link to that email thread? I would like to take a closer
look at that discussion.

> As a consequence, I think it would be a great addition to your current work a version of the macro BOOST_LOCALFUNCTION macro that executes in place. It just needs a different macro name (ex: BOOST_IMMEDIATEFUNCTION), without the function name, without the function return type, and without the functor.
>
> So basically a wrapper around :
> { BOOST_SCOPE_EXIT()
>  {
>
>
>  }
>  BOOST_SCOPE_EXIT_END();
> }
> which binds also the 'this', and constness like you did, should do the trick.
> What do you think of this proposition?

Yes but how is this different than just executing the code within a
local code block `{ ... }`? Why is it necessary to wrap the code
within the local function if the local function has no parameter and
it is executed only once right after its definition?

One (the only?) reason I can think of for local functions with no
parameters and single immediate execution is to implement
constant-correct code blocks -- which were my original need for local
functions in Boost.Contract. For example:

void f(int x) {
    int y = x;

    const { // Const-block but doesn't work in C++ :(
        assert(y == x); // Within const-block so compiler error if I
mistake this with `y = x`.
    }

    ...
}

C++ does not support const-blocks `const { ... }` but local function's
const-bound parameters can be used for that:

void f(int x) {
    int y = x;

    { // Create inner scope so I can use the name `check()` multiple
times without clashes.
        BOOST_LOCAL_FUNCTION(
        (void) (check)( (const bound)((&x)(&y)) )
        ) {
            assert(y == x); // Now I get compiler error if I mistake
this with `y = x`.
        } BOOST_LOCAL_FUNCTION_END(check)
        check(); // Execute immediately and just once.
    }

    ...
}

In fact, if I submit my Boost.LocalFunciton I will also propose and
submit the macros `BOOST_CONST_BLOCK() / BOOST_CONST_BLOCK_END` to
support const-blocks expanding to the local function code listed
above. Using these macros the example above becomes:

void f(int x) {
    int y = x;

    BOOST_CONST_BLOCK( (x)(y) ) {
        assert(y == x); // Now I get compiler error if I mistake this
with `y = x`.
    } BOOST_CONST_BLOCK_END

    ...
}

(Note these macros alway and automatically bind the specified
variables as `const&`.)

> 2/ Is it possible to have look at your code?

Of course and thanks for the interest! However, give me a couple of
weeks so I can clean up the code and add a couple of examples. Then I
will post a link to the source.

> 3/ What is the generated code output by your example ?

Same as above, I will post the code in a couple of weeks.

> 4/ do you think your work could be use to allow Boost.ScopeExit to use your 'this' binding and constness techniques ?

Yes, Boost.ScopeExit main macros can be now re-written using
Boost.LocalFunction so to support both `const bound` parameters and
`this`. I will add an example on how to implement Boost.ScopeExit
using Boost.LocalFunction (really Boost.LocalFunction is implemented
using all Boost.ScopeExit then just the outer macros so
Boost.ScopeExit can be re-written using Boost.LocalFunction).

-- 
Lorenzo

Boost list run by bdawes at acm.org, gregod at cs.rpi.edu, cpdaniel at pacbell.net, john at johnmaddock.co.uk