How to break const

deadalnix deadalnix at gmail.com
Wed Jun 20 00:16:51 PDT 2012


Le 19/06/2012 17:49, Timon Gehr a écrit :
> On 06/18/2012 11:04 PM, deadalnix wrote:
>> Le 18/06/2012 17:29, Timon Gehr a écrit :
>>> On 06/18/2012 05:14 PM, Christophe Travert wrote:
>>>> Matthias Walter , dans le message (digitalmars.D:170036), a écrit :
>>>>> On 06/18/2012 07:36 AM, Mehrdad wrote:
>>>>>> Is it just me, or did I subvert the type system here?
>>>>>>
>>>>>>
>>>>>> import std.stdio;
>>>>>>
>>>>>> struct Const
>>>>>> {
>>>>>> this(void delegate() increment)
>>>>>> { this.increment = increment; }
>>>>>> int a;
>>>>>> void delegate() increment;
>>>>>> void oops() const { this.increment(); }
>>>>>> }
>>>>>>
>>>>>> void main()
>>>>>> {
>>>>>> Const c;
>>>>>> c = Const({ c.a++; });
>>>>>> writeln(c.a);
>>>>>> c.oops();
>>>>>> writeln(c.a);
>>>>>> }
>>>>>>
>>>>>
>>>>> I don't think so. When calling oops you have two references to the
>>>>> object c:
>>>>>
>>>>> - The this-pointer of the object itself which is not allowed to change
>>>>> the object in the const-call.
>>>>> - The reference from within main which is allowed to change it and can
>>>>> be reached via the frame pointer of the delegate.
>>>>>
>>>>> I see this as perfectly valid code. Of course, opinions may differ
>>>>> here.
>>>>
>>>> But here, the frame pointer of the delegate is part of the const
>>>> structure. By transitivity, the frame pointer should be const, ...
>>>
>>> 'By transitivity' is not a sufficient reason. What you really mean is
>>> 'For the guarantee that a const pure method does not change its mutable
>>> parameters'.
>>
>> Transitivity by itself is required to solve a wide range of problem. The
>> most obvious one is controlling what is shared and what isn't using the
>> type system.
>
> That is completely unrelated.
> It is impossible to justify transitivity of const for delegate context
> pointers using this argument. It is far too general and the
> justification for the general concept comes from a specific example
> that is different from the one at hand.
>
> The question is, what the meaning of 'const' references should be:
>
> 1. data cannot be changed transitively through the reference
>
> 2. the reference can reference both 'const' and 'immutable' data and
> 'immutable' data can transitively not be changed through the
> reference.
>
>
> 1. requires transitive const for delegate context pointers, 2. does not.
>

No, 2. require 1., even if the initialization is broken.

class Foo {
     void delegate() dg;

     this(immutable void delegate() dg) immutable {
         thid.dg = dg;
     }
}

Now, as delegate doesn't carry the constness of its context, an 
immutable instance of Foo can refers to something that isn't immutable.


More information about the Digitalmars-d mailing list