[C++-sig] Re: Adding __len__ to range objects

Raoul Gough RaoulGough at yahoo.co.uk
Mon Aug 25 14:04:58 CEST 2003


"Joel de Guzman" <djowel at gmx.co.uk> writes:

> Raoul Gough <RaoulGough at yahoo.co.uk> wrote:
>> "Joel de Guzman" <djowel at gmx.co.uk> writes:
>
> Hi Raoul,
>
> I'll reply to your other "ramblings" (;-) later. For now the most easiest
> to reply to:
>
>>> Following Pythion semantics, basically, we want this:
>>> 
>>>     val = c[i]
>>>     c[i].m()
>>>     val == c[i]
>>> 
>>> where m is a non-const (mutating) member function (method). Yet, we
>>> also want this:
>>> 
>>>     val = c[i]
>>>     del c[i]
>>>     # do something with val
>>> 
>>> No dangling references == no return_internal_reference
>>> 
>>> 
>>> A proxy is basically a smart-pointer that has a reference to a
>>> container and an index. When *attached*, dereferencing the proxy
>>> will index the container. A proxy can be detached from the
>>> container. In the *detached* state, it holds the actual object which
>>> it returns when dereferenced. A proxy will be detached whenever you
>>> remove or replace that element from the container (e.g. del C[I],
>>> C[0:I] = [a,b,c], C[I] = x).
>>> 
>>> The proxy_group manages the proxies and is responsible for detaching
>>> a proxy appropriately when necessary.
>> 
>> Well, I've got to admire that for dedication to Python semantics! I
>> can think of an alternative, though, that would simplify the suite
>> considerably: document a requirement that if the client code wants
>> Python-style semantics it should use a container of shared_ptr. This
>> obviously has some disadvantages over the proxies, but I think it
>> achieves the same semantics without any additional complexity in the
>> indexing suite.
>
> Can't do. Remember, one of the main objectives of BPL is to (quoting the
> manual):
>
> " It is designed to wrap C++ interfaces non-intrusively, so that you should 
> not have to change the C++ code at all in order to wrap it, making Boost
> Python ideal for exposing 3rd-party libraries to Python.". 

Personally, I prefer the smart pointer approach - "as safe as
possible, but no safer" :-) I take your point, though.

>
> Forcing the client to wrap containers of shared_ptr goes against this goal. 
> As a matter of fact, what actually spurred the development of the indexing 
> suite was because I needed to wrap some special vectors of objects. It is 
> out of the question to go modifying the C++ code.

Well, my concern is to do with the complexity of the support - it
seems to require hooks throughout all of the code that modifies the
container. Maybe it would be possible to create a "container proxy"
that emulates the vector interface, and use:

indexing_suite <container_proxy <std::vector<MyType> > >

Thus encapsulating the proxy code. I think this would localize the
code much better, if it is possible to do.

Another concern about this - have you considered cases where C++ code
accesses the raw container (i.e. without going via the indexing
suite)? e.g.

    val = c[i]
    cxx_function(c)
    val == c[i]  # ??

where cxx_function might (from C++) insert something into the
container. If I understand correctly, doing an insertion via the
indexing suite would notify the proxy when it needs to update its
index. I think that means that raw C++ code that modifies the
container would cause problems.

So what do you think of the idea of providing a proxy-container-
wrapper, instead of integrating the proxy support directly into the
indexing suite? C++ code would then be aware (and have direct access
to) the wrapped container, and it might significantly simplify the
internals of the indexing suite.

-- 
Raoul Gough
"Let there be one measure for wine throughout our kingdom, and one
measure for ale, and one measure for corn" - Magna Carta





More information about the Cplusplus-sig mailing list