mutable keyword

Jonathan M Davis via Digitalmars-d-learn digitalmars-d-learn at puremagic.com
Fri May 20 17:39:21 PDT 2016


On Friday, May 20, 2016 21:35:27 ciechowoj via Digitalmars-d-learn wrote:
> On Friday, 20 May 2016 at 20:45:05 UTC, Jonathan M Davis wrote:
> > If you want something that's ref-counted and works in pure
> > code, const will _not_ work, because you can't legally alter
> > the ref-count.
>
> What about something like this (ignoring multi-threading issues):
>
> struct RefCountPool {
>     size_t acquireIndex();
>     void releaseIndex(size_t index);
>
>     size_t* accessRefCounter(size_t index);
> }
>
> RefCountPool refCountPool;
>
> struct SharedPtr
> {
>     size_t index;
>     void* ptr;
>
>     SharedPtr(void* ptr) {
>         this.ptr = ptr;
>         index = refCountPool.acquireIndex();
>     }
>
>     // more methods, counter manipulation through accessRefCounter
> }
>
> Is is still legal? Would it breach @pure requirements (I believe
> so...)? After all it doesn't differs much from having a pointer
> instead of index.

Well, if you actually tried marking functions with pure, you'd see pretty
fast that this won't work with pure. A function that's marked with pure
cannot access any global, mutable state. It can only access what's passed to
it (though in the case of a member function, that includes the this
pointer/reference). So, your refCountPool will not be accessible from any
pure functions.

You can think of pure as @noglobal, because it can't access global variables
(unless they're constants). That's it's only restriction, but it's enough to
make it so that the only way that you'd have a backdoor out of const in a
pure, const member function is if you passed a mutable reference to the
object as one of the function arguments.

At this point, if you want ref-counting, you give up on const. They simply
do not go together. The same goes for stuff like caching or lazy
initialization.

Sure, you can get around const to some extent by giving up on pure, but that
only works because you're putting the state of the object outside of the
object itself, which is usally a bad idea. It also makes it so that const
seems like a lie, since the state of the object isn't really const, since
it's not actually in the object.

The standard library already has std.typecons.RefCounted, if you want to
ref-count anything other than classes, but it really doesn't work with const
and fundamentally can't. In order to have const ref-counting, we're going to
need language support. D does not and likely will never have any form of
"logical" const. If it's const, it's const. Either that fits with what
you're doing, and you can use const, or it doesn't, and you can't.

- Jonathan M Davis



More information about the Digitalmars-d-learn mailing list