II
Size: a a a
II
II
II
II
SK
MB
def map = new ConcurrentHashMap<String, String>()
map.computeIfAbsent("A", { key ->
return map.computeIfAbsent("B", {k -> "hello"}) + "ForA"
})
println(map)
// --------
def map2 = new ConcurrentHashMap<String, String>()
def bValue = map2.computeIfAbsent("B", {k -> "hello"})
map2.computeIfAbsent("A", {key -> bValue + "ForA"})
println(map2)
MB
SK
def map = new ConcurrentHashMap<String, String>()
map.computeIfAbsent("A", { key ->
return map.computeIfAbsent("B", {k -> "hello"}) + "ForA"
})
println(map)
// --------
def map2 = new ConcurrentHashMap<String, String>()
def bValue = map2.computeIfAbsent("B", {k -> "hello"})
map2.computeIfAbsent("A", {key -> bValue + "ForA"})
println(map2)
MB
SK
SK
B, результат которого зависит от двух A (по определению, эту часть хотелось бы не подвергать переписыванию). И B, и А должны быть мемоизированны при первом вычислении (и должна быть гарантия что вычисление каждого из heavylifting методов происходит не более одного раза). При этом клиентская сторона может потенциально вызвать их в рандомном порядке (сэмулированно в мэйне), и конкуррентно (пока для простоты никак не сэмулированно). Если раннать мейн, он будет виснуть с некоторой вероятностью (если B пойдет вычисляться раньше чем обе A, будет дэдлок)II
SK
B, результат которого зависит от двух A (по определению, эту часть хотелось бы не подвергать переписыванию). И B, и А должны быть мемоизированны при первом вычислении (и должна быть гарантия что вычисление каждого из heavylifting методов происходит не более одного раза). При этом клиентская сторона может потенциально вызвать их в рандомном порядке (сэмулированно в мэйне), и конкуррентно (пока для простоты никак не сэмулированно). Если раннать мейн, он будет виснуть с некоторой вероятностью (если B пойдет вычисляться раньше чем обе A, будет дэдлок)II
public static <T> T memoizedCalculation2(Cache cache, Key key, Callable<T> calculation) {
Cache.ValueWrapper val = cache.get(key);
if (val == null) {
try {
T newVal = calculation.call();
Cache.ValueWrapper oldVal = cache.putIfAbsent(key, newVal);
return oldVal == null ? newVal : (T) oldVal.get();
} catch (Exception ex) {
throw new RuntimeException(ex);
}
}
return (T) val.get();
}SK
public static <T> T memoizedCalculation2(Cache cache, Key key, Callable<T> calculation) {
Cache.ValueWrapper val = cache.get(key);
if (val == null) {
try {
T newVal = calculation.call();
Cache.ValueWrapper oldVal = cache.putIfAbsent(key, newVal);
return oldVal == null ? newVal : (T) oldVal.get();
} catch (Exception ex) {
throw new RuntimeException(ex);
}
}
return (T) val.get();
}II
SK
II
SK
II