我们假设我获得了整数x
和y
(x <= y
满足0
的数字,因此它们特别可以被2整除)。然后我知道他们的平均avg = ((x+y) / 2)
也是一个整数。我想找到这个中点四舍五入到100
的分辨率。换句话说,如果我的两个输入是75200和75300,那么平均值是75250并向上舍入到最接近的100
(但不超过或等于更大的数字)迫使答案为75200。
如果不首先将所有内容除以100并使用以下浮点运算,我该如何实现此逻辑:
x + std::floor((y - x) * .5 * 100 + .5)*0.01
换句话说,如何在没有浮点值的情况下执行上述操作,但在100
而不是0.01
的分辨率下获得相同的行为?
答案 0 :(得分:3)
计算你可以做的平均值
avg = (x + y) / 2
(BTW,即使在小型微控制器上,整数加法除以2也是非常便宜的操作。)
要将此舍入为最接近的100的倍数(对应于您的浮点示例),您可以执行
result = ((avg + 50) / 100) * 100
整数除法向下舍入到最接近的整数。通过将50
更改为0
,您可以始终向下舍入,同时将其更改为99
始终向上舍入。
编辑:请注意,此舍入方法不适用于负数。由于整数除法向零舍入,在这种情况下,您需要减去50
,减去99
以总是向下舍入并减去0
以便始终向上舍入。
答案 1 :(得分:2)
您的问题示例需要强大的条件:
因此,对于大多数情况,简单的舍入平均值非常适合您:
avg100 = avg - (avg % 100) + 100
棘手的部分是在没有条件的情况下修复剩余的错误 - 如果你想避免条件或减慢操作。
为此,最好的方法是使用乘法,并将表达式拆分为两个:
avg100 = avg - (avg % 100)
avg100 += 100 * !!(y - avg100)
对于大多数情况,y大于avg100。对于这种情况,!!
运算符将返回1.在极少数情况下,当它们相等时,它将返回0,并且不会更改该值。
(我不知道编译器是否真的会为'!!'运算符生成一个没有条件的代码,但是我没有一个击球手的想法,如果有可能,我认为它会。如果没有,这段代码仍然简短易懂。)
此外,您可以使用以下表达式计算平均值:
avg = y - (y-x)/2
甚至可以将划分更改为位移以进行优化。
这不需要两个数字都是偶数,只需要相同的奇偶校验。