Computed Constant feature request
Per-Ake Minborg
per-ake.minborg at oracle.com
Mon Aug 21 07:16:36 UTC 2023
Hi David!
Thank you for the encouragement.
As it turns out, you still get the constant-folding benefit if you create a Map using (for example) Map.of or Collectors.toUnmodifiableMap and then provide individual
ComputedConstans.of(size, mapper) as a replacement for your LargeList. But maybe you want to create your LargeList in one sweep?
I have experimented a bit with Maps containing ComputedConstant instances for a while. There is nothing preventing us from adding it later on. Maybe not in the first incarnation of ComputedConstants.
Here is a sketch of one of the many Map variants contemplated:
/**
* {@return a new unmodifiable Map of {@link ComputedConstant } values with the provided
* {@code keys} and provided {@code presetMapper}}
* <p>
* The Map and its values are eligible for constant folding optimizations by the JVM.
* <p>
* Below, an example of how to cache values in a Map is shown:
* {@snippet lang = java:
* class DemoMap {
*
* private static final Map<Integer, ComputedConstant<User>> USER_ID_CACHE =
* ComputedConstant.of(List.of(0, 1, 1000), DB::findUserById);
*
* public User userFromCache(int userId) {
* return USER_ID_CACHE.get(userId);
* }
* }
*}
*
* @param <K> the type of the keys
* @param <V> the type of the values
* @param keys the keys to associate with ComputedConstant instances
* @param presetMapper the mapper to apply when computing values
*/
static <K, V> Map<K, ComputedConstant<V>> of(Collection<K> keys, Function<? super K, ? extends V) presetMapper) {
Objects.requireNonNull(keys);
Objects.requireNonNull(presetMapper);
...
}
The above javadoc example will create a Map with the keys 0, 1, and, 100 for which the bound values of the ComputedConstants will be computed
by invoking the provided mapper that presumably will look up users in a database upon being referenced the first time.
This would allow you to do something like this:
Map<MyEnum, ComputedConstant<LargeList<MyResource>> map =
ComputedContant.of(EnumSet.allOf( MyEnum.class ), SomeUtil::fetchLargeListOfMyResource);
MyResource myFooResource0 = map.get(MyEnum.FOO).get().get(0);
Let me know your thoughts on this.
Best, Per
________________________________
From: leyden-dev <leyden-dev-retn at openjdk.org> on behalf of David Alayachew <davidalayachew at gmail.com>
Sent: Sunday, August 20, 2023 1:36 AM
To: leyden-dev <leyden-dev at openjdk.org>
Subject: Computed Constant feature request
Hello Leyden Dev Team,
I am very excited for the ComputedConstant JEP that has been recently announced. There are lots of places in my current projects that could use a feature like this.
Today, for example, I want to lazy load a gigantic list of resources (>100). However, these resources are not fetched via an index, they are fetched via a key.
My current data type that I am storing them into is essentially a Map<MyEnum, LargeList<MyResource>>. I would like to be able to swap out this map for a ComputedConstant that can give me my LargeList<MyResource> when I provide it an instance of MyEnum.
I could technically create a mapper that takes in MyEnum, turns it into its ordinal, and then does something like this.
ComputedConstant
.of
(
MyEnum.values().length,
i -> fetchLargeListOfMyResource(MyEnum.values()[i])
)
;
But I'd like to avoid that if at all possible. It feels like I would end up right back into that error-prone territory from before.
Is this feature possible and worth doing as part of this JEP?
Thank you for your time and help!
David Alayachew
-------------- next part --------------
An HTML attachment was scrubbed...
URL: <https://mail.openjdk.org/pipermail/leyden-dev/attachments/20230821/d7fb5ffb/attachment.htm>
More information about the leyden-dev
mailing list