bye stable values, enter lazy constants

Sergey Bylokhov bylokhov at amazon.com
Mon Sep 29 20:39:26 UTC 2025


On 9/29/25 12:51, Maurizio Cimadamore wrote:
> The point remains: lazy doesn't imply "only one" -- so, I don't buy that
> Lazy<T> is "good enough" (although I agree it's much shorter to type --
> which is, I think, the real argument here?)

I have two points about this (and yes, naming is hard):
  - First, why does "lazy" not imply "only once"? We already have an example of such an API: 
records. Does the word "record" explicitly imply that its components can only be assigned once? We 
implemented and documented it that way. Similarly, we can document the behavior for the new 
interface/class to clarify that laziness also means "stability".
  - Second, the main argument here is about the "Constant" part. The API is being compared to the 
final keyword and is positioned as an improvement, since it allows lazy initialization while still 
enabling the JVM to optimize everything. This optimization capability is emphasized by the 
"Constant" in the name. But if the field itself is not declared final, that undermines the whole 
argument.

In that sense, I felt StableValue was a better name, but perhaps we can come up with something even 
more suitable.

> Overall it is not quite clear to me what is the main point you are
> trying to make. Once you buy this is an API and not a language feature
> (and I understand you don't fully buy that), and once you buy its name
> (as verbose as it might be), are there ways in which the proposed API
> seems insuficient?

I was just trying to think of possible alternatives. For example, have we considered something 
similar to @FunctionalInterface, like a @PureInterface (or any other mechanism to introduce pure 
functions) interfaces that behave like functional ones but also allow result caching?

As for the current proposal, it feels somewhat unnatural that the API is split between LazyConstants 
and Map/List. I think it needs some time and experimentation to see how it plays out in practice.


> When you have lots of fields, using a lazy list provides quite a big win
> compared to having separate holders (we made experiments with our
> jextract tool which demonstrate this) -- because you can have a single
> lambda/class for _all_ the elements. So you get the same performance as
> having one holder class for each element, w/o really having one holder
> for each element.

This argument is overly focused on performance. It suggests that exposing many unrelated fields in a 
class is acceptable if it leads to better performance. While that might be beneficial for generated 
code, in manually written code, clarity might be more important than performance.

I hope we can achieve both goals: good performance and proper encapsulation.

-- 
Best regards, Sergey.


More information about the leyden-dev mailing list