On Mon, Apr 04, 2022 at 11:20:31AM -0700, Ali Çehreli via Digitalmars-d-learn 
wrote:
> On 4/3/22 17:42, H. S. Teoh wrote:
> 
> > In some sense, this is like an extension of ctors initializing
> > immutable values. The compiler tracks whether the variable has been
> > initialized yet, and inside the ctor you can assign to immutable
> > because the uninitialized value is not observable from outside
> > before that. Once assigned, the compiler enforces no subsequent
> > changes.
> 
> These ideas make sense to me.
> 
> I remember reading somewhat similar requests in the past: Assign to a
> variable freely but at some point say "no more mutation to this
> variable".
[...]

It's not just "assign freely"; it's "assign once". Or rather, "assign
before the outside world sees it".

In fact, now that I think of it, I wonder if this could actually be
implementable in the current language. Here's a first stab at it:

        struct LazyValue(T) {
                private class Impl
                {
                        immutable T value;
                        this(immutable T v) { value = v; }
                }
                private Impl impl;
                private T delegate() pure generate;
        
                this(T delegate() pure _generate)
                {
                        generate = _generate;
                }
        
                immutable(T) get() {
                        if (impl is null)
                                impl = new Impl(generate());
                        return impl.value;
                }
                alias get this;
        }
        
        void main() {
                import std;
                auto lazyInt = LazyValue!int({ return 123; });
                writeln(lazyInt.get);
        }

Currently generate() has to be pure, which limits the utility somewhat
(you couldn't load the value from a file, say).  But in principle, the
approach seems to work.


T

-- 
Obviously, some things aren't very obvious.

Reply via email to