Safe cast away from immutable

Jonathan M Davis via Digitalmars-d digitalmars-d at puremagic.com
Mon Feb 8 13:48:30 PST 2016


On Monday, 8 February 2016 at 21:14:11 UTC, Iakh wrote:
> On Monday, 8 February 2016 at 20:43:23 UTC, Jonathan M Davis 
> wrote:
>> in a bug report should be sufficient to show the bug, even 
>> without the rest of what you're doing.
>>
>> In general, it should be impossible for member functions to be 
>> considered strongly pure unless they're marked as immutable, 
>> though the compiler could certainly be improved to determine 
>> that no escaping of the return value or anything referencing 
>> it occurs within the function and that thus it can get away 
>> with treating the return value as if it's the only reference 
>> to that data, but that would likely be farther into the realm 
>> of code flow analysis than the compiler typically does.
>
> It does. A bit. If S.arr is int[] the program fails to compile.
> Is all prams being const(but not immutable) not enough for
> function to be Pure?

Whether the function can be pure or not has nothing to do with 
const or immutable. All that pure means in and of itself is that 
the function cannot access any module-level or static variables 
whose state can ever change after they're initialized (though 
immutable is fine, and const is fine if there can't be any other 
references to the same data). So, every bit of state that can 
change over the course of the program that a pure function can 
access is through its arguments (which includes the invisible 
this pointer/reference in the case of member functions).

Now, depending on the types of the arguments, the compiler can do 
various optimizations. The most basic would be that if all of the 
arguments are immutable, then if the same values are given, the 
compiler can elide multiple calls - e.g. pureFunc(a) * 
pureFunc(a) could just call pureFunc once and then reuse the 
result rather than calling it twice as would occur normally.

One of the most useful things that the compiler can do if a 
function is pure is that if it can guarantee that the return 
value did not get passed in as an argument or was otherwise 
obtained via an argument, then it knows that the argument was 
created within the function and that therefore the return value 
is the only reference to that data, and so it's safe to alter its 
mutability - e.g. change a mutable array to an immutable one. 
Exactly which conditions under which that can be determined to be 
safe are not exactly straightforward. The simplest is when all of 
the arguments were immutable, but there are others, some of which 
are much more complicated (and under some circumstances, const 
can help with that, whereas in others, it can't - it really 
depends on the types involved). I don't know how sophisticated 
the compiler is in determining that right now, but clearly, what 
it currently has is buggy, because it failed to take the 
invisible this pointer/reference into account in your example and 
thus incorrectly determined that it was not possible for another 
reference to the same data to exist after the function returned.

>> Regardless, your example definitely shows a bug. Please report 
>> it. Thanks.
>
> Done
> https://issues.dlang.org/show_bug.cgi?id=15660

Thanks.

- Jonathan M Davis


More information about the Digitalmars-d mailing list