【算法】带四舍五入的整除
在嵌入式开发上使用浮点数等于作死。#define DIVIDE_WITH_ROUND(N, D)(((N) == 0) ? 0:((((N) * 2)/(D)) + 1)/10)
经测试,在特殊情况下依然有误差。要根据实际的使用需求来使用它。
在单片机平台上,使用这种除法来实现LCD屏幕绘制斜线,效果比较好。贴近于你在PC上用浮点数+SetPixel来绘制斜线。和GDI的MoveToEx()、LineTo()的效果非常接近。
参考资料:
https://stackoverflow.com/questions/2422712/rounding-integer-division-instead-of-truncating/18067292
https://en.wikipedia.org/wiki/Line_drawing_algorithm N 和D似乎需要括号! Ayala 发表于 2018-4-11 20:13
N 和D似乎需要括号!
已更新 计算机上修约一般采用4舍6入5取偶的方式 本帖最后由 Ayala 于 2018-5-5 21:11 编辑
(N) / (D)\
+ ((N) % (D)) * 2 > (D) \
? 1 \
: (((N) % (D)) * 2 < (D) \
? 0 \
: ((N) / (D)) & 1 == 0\
? 0 \
: 1)
不知道语法有没有错误! #define DIVIDE_WITH_ROUND(N, D)(((N) == 0) ? 0 : ((((N) * 2)/(D)) + 1)/10) // 你确定最后是除10?前面 * 2,后面应该 / 2 才平衡啊!
// 重新优化一下(* 2 和 / 2 可以用位移优化):
#define DIVIDE_WITH_ROUND(N, D)(((N) == 0) ? 0 : ((((N) << 1) / (D)) + 1) >> 1)
// 如果再考虑一下有符号运算(我不确定N的位数,不敢直接用位运算取符号位,所以用更稳妥的比较运算代替):
#define DIVIDE_WITH_ROUND(N, D)(((N) == 0) ? 0 : ((((N) << 1) / (D)) + ((N) > 0)) >> 1)
学习了,谢谢
页:
[1]