Representing State as Interfaces in Go
emoses.org
emoses.org
I can't remember who gave this talk, but a prime example is a `File` type. A `File` type shouldn't have a Read() method until the file itself has opened. And calling `Close()` on the File should prevent further reads. Substructural typing - and this pattern - allows you to refine types based off of the type's instance state.
There's a ton possible here but I haven't really kept up to date with type systems in the last 5 years. Stuff like this has probably advanced a ton!
It wouldn't make much sense. The whole point is not needing a new one, but reusing the record.
The given example looks like a Builder pattern. Although that name smells strongly of Java, so Go users might prefer to avoid it. :)
I wanted to express that having functions
f(a) -> b {}
f(b) -> c {}
f(c) -> d {}
...
would be quite trivial.I would say that the whole point of the builder pattern is _not_ having an ordering of the "chained" functions.
That seems like the same thing as the example in the original post.
built = empty().configA(a).configB(b). ... .configZ(z)
where each config?(this : T, k : K) -> T
For me the defining feature of a builder is the (possibility of a) gradual "configuration" (or whatever) of the data structure being "built". A state change is something else in my opinion, but of course, the difference between a "state change" and a "configuration" (which does change state) isn't a clear one, so if for you that is still a builder, that's fine for me too ;).[0] https://fsharpforfunandprofit.com/posts/designing-with-types...
It might work in a language with linear types or some concept of ownership. Execute() would take ownership of the Resolver and prevent it being called again.
Java folks might have a name. It's similar to the Foo().bar().baz() constructor pattern.
¹ Edit to add: well, it's a pattern I've seen a lot, anyway. I think it's preferable to mutating the final object in place because it "makes illegal states unrepresentable" as others in this discussion have mentioned.
For some reason I only see Rustaceans talking about it, though it's perfectly applicable in any language with static typing.
And then of course Rust people care about correctness more in general.