int scaled, translatedAndScaled; // low <= translatedAndScaled < high
scaled = (int) Math.random() * (high - low);
translatedAndScaled = low + scaled;
Why?
Since the lowest value returned by Math.random() is 0, and the highest value is just under 1, we have:
0 = 0 * (high - low) <= Math.random() * (high - low) < 1 * (high - low) = high - low
or, more simply
0 <= Math.random() * (high - low) < high - low
By adding low to this, we obtain:
low <= low + Math.random() * (high - low) < high - low + low = high
Thus, low <= translatedAndScaled < high.