/** * Returns the current value. The returned value is <em>NOT</em> * an atomic snapshot; invocation in the absence of concurrent * updates returns an accurate result, but concurrent updates that * occur while the value is being calculated might not be * incorporated. * * @return the current value */ public long get() { Cell[] cs = cells; long result = base; if (cs != null) { for (Cell c : cs) { if (c != null) { result = function.applyAsLong(result, c.value); } } } return result; }
/** * Updates with the given value. * * @param x the value */ public void accumulate(long x) { Cell[] cs; long b, v, r; int m; Cell c; if ((cs = cells) != null || ((r = function.applyAsLong(b = base, x)) != b && !casBase(b, r))) { boolean uncontended = true; if (cs == null || (m = cs.length - 1) < 0 || (c = cs[getProbe() & m]) == null || !(uncontended = (r = function.applyAsLong(v = c.value, x)) == v || c.cas(v, r))) longAccumulate(x, function, uncontended); } }
/** * Equivalent in effect to {@link #get} followed by {@link * #reset}. This method may apply for example during quiescent * points between multithreaded computations. If there are * updates concurrent with this method, the returned value is * <em>not</em> guaranteed to be the final value occurring before * the reset. * * @return the value before reset */ public long getThenReset() { Cell[] cs = cells; long result = getAndSetBase(identity); if (cs != null) { for (Cell c : cs) { if (c != null) { long v = c.getAndSet(identity); result = function.applyAsLong(result, v); } } } return result; }
long lout = lt.out; rt.in = (l == org ? lout : fn.applyAsLong(pin, lout)); for (int c;;) { if (((c = rt.getPendingCount()) & CUMULATE) != 0) a[i] = sum = fn.applyAsLong(sum, a[i]); sum = fn.applyAsLong(sum, a[i]); long lout = lt.out; par.out = (rt.hi == fnc ? lout : fn.applyAsLong(lout, rt.out));
long lout = lt.out; rt.in = (l == org ? lout : fn.applyAsLong(pin, lout)); for (int c;;) { if (((c = rt.getPendingCount()) & CUMULATE) != 0) a[i] = sum = fn.applyAsLong(sum, a[i]); sum = fn.applyAsLong(sum, a[i]); long lout = lt.out; par.out = (rt.hi == fnc ? lout : fn.applyAsLong(lout, rt.out));
wasUncontended = true; // Continue after rehash else if (c.cas(v = c.value, ((fn == null) ? v + x : fn.applyAsLong(v, x)))) break; else if (n >= NCPU || cells != cs) ((fn == null) ? v + x : fn.applyAsLong(v, x)))) { break done;