On Thursday, 14 June 2012 at 11:11:57 UTC, Jonathan M Davis wrote:
I haven't had the chance to look over your code yet, but this looks _seriously_ suspect. Casting to and from immutable or cast away const are things that should be done _very_ rarely. One of the few times that casting to immutable makes any sense is when you need an object to be mutable while you put it together and then immutable afterwards. But when you do that, that
reference or pointer is the _only_ reference to that data. e.g.

auto func(size_t numElems)
{
    auto arr = new int[](numElems);

    foreach(ref e; arr)
      //do something to initialize e

    return cast(immutable int[])arr;
}

Taking a function's parameter (which came from who-knows-where) and casting it to immutable is almost certainly a terrible thing to do. If there are _any_ other references to that data, you will have bugs. immutable is supposed to guarantee that the data is _never_ altered. So, when you cast something to immutable, you're telling the compiler that it's okay to treat that data as immutable and that you will _not_ have any mutable references to that data or alter it in any way. If you do, you'll be breaking the compiler's guarantees.

Ideally, you would always construct immutable objects as immutable rather than creating them as mutable and then casting them to immutable, but that's not
always possible.

And taking your payload, which is immutable, and casting away immutable when you return it from front is truly bad. Casting away const or immutable and then mutating that object is _undefined_ behavior. Do _not_ do it unless you
have to and know what you're doing.

These stackoverflow questions may help you understand better:

http://stackoverflow.com/questions/4219600/logical-const-in-d
http://stackoverflow.com/questions/10364837/why-do-i-have-to-cast-this

- Jonathan M Davis
OK, clear. Thanks!

I was thinking that casting is bad here, but wanted to give the user ability to pass any object inside constructor. Now I see that this is a bad idea given transitivity of immutable.

In .NET readonly applies only to fields inside objects preventing assignments to them from other places than constructors. But I can assign another instance of an object with readonly fields to the same variable. Then I can pass that instance to some constructor and assign it to a readonly field.

How to achieve the same in D? As far as I understand, it is not possible for structs with immutable fields, and it is not clear for me about classes.

In other words:

Does a variable always point to the same place in memory and assigning to it simply copies data to that place? I don't understand whether it is possible to make it point to another place. That would be a mutable variable pointing to a type with immutable fields. After that I want to assign an instance of that type to an immutable field in constructor. Can I do so, or that would be bad?

Reply via email to