On 06/25/2013 10:13 PM, Peter Levart wrote: > > On 06/22/2013 12:54 PM, Aleksey Shipilev wrote: >> T get(int index1, index2) { >> T[][] lc = cache; >> if (index1 >= lc.length) { // needs resizing >> lc = <generate_new_T[][]_of_size>((index1 << 1) + 1); >> cache = lc; >> } >> T[] lt = lc[*index2*]; >> if (index2 >= lt.length) { // needs resizing >> lt = <generate_new_T[]_of_size>((index2 << 1) + 1); >> lc[index1] = lt; >> cache = lc; // publish >> } >> return lt[index2]; >> } >> >> -Aleksey. > > Hi Aleksey, > > 1st I think there's a typo in above bolded part. There should be index1 > instead of index2 there, right?
Nope, lc is indexed with index2; lt is indexed with index1. > Then I think there's a data race in above code which can de-reference > half-constructed array and an element within it: Damn. Good point, let's discuss that in the appropriate RFR, see 8017540. > I have studied the constraints of powerCache and have observed: > So the caching could be performed with no synchronization (other than > that provided by final fields descibed above). Yeah, we can do that with finals. Too bad you can't have the final semantics with BigInteger[] array. > Here is a possible variant of such caching: Seems overcomplicated. ;) Let's instead fix the code proposed in 8017540. Thanks, Aleksey.