Why use low + (high-low) / 2 instead of (high + low) / 2?

Why use low + (high-low) / 2 instead of (high + low) / 2? The purpose is to prevent overflow!
Why does this prevent overflow? Look at the example below.

high = 0100 0000 0000 0000 0000 0000 0000 0000 = 1073741824
 low = 0100 0000 0000 0000 0000 0000 0000 0000 = 1073741824

Then we add these two values ​​together and see what the result is.

high + low =  1000 0000 0000 0000 0000 0000 0000 0000
           =  2147483648 as unsigned 32-bit integer
           = -2147483648 as signed   32-bit integer
	(high + low) / 2   = 1100 0000 0000 0000 0000 0000 0000 0000 = -1073741824
	(high + low) >>> 1 = 0100 0000 0000 0000 0000 0000 0000 0000 =  1073741824
low + (high - low) / 2 = 0100 0000 0000 0000 0000 0000 0000 0000 =  1073741824

As a signed 32-bit integer, it overflows and flips to negative. Therefore, it (high + low) / 2is wrong, because high + lowthe result of the operation may exceed the range represented by the current type.

If operated as an unsigned 32-bit integer, the sum is correct. All it takes is to divide it by 2.

Unsigned integers are not supported in Java operations, so we generally choose low + (high-low) / 2 to prevent overflow, but there is a way to write low + (high-low) >>> 1, in Java> The difference between >> and >> lies in unsigned and signed. If you use >>, the sign bit will also participate in the calculation.

(high + low) >> 1 = 1100 0000 0000 0000 0000 0000 0000 0000 = -1073741824

Generally speaking, >> and >>> are more efficient than dividing /, but after optimization by the compiler, their efficiency is not much different. Try to be consistent with your colleagues in your work. Do not use bitwise operations without authorization. This may cause problems. It causes difficulty in reading, and the efficiency cannot be improved much.
If there are deviations or errors in my understanding in the article, please comment and point out the readers, it is greatly appreciated.

Guess you like

Origin blog.csdn.net/weixin_44556968/article/details/110288725