无论在哪个平台上,权重之和都应该是1.0
sum of weights should be exactly 1.0 no matter on which platform it is
我有这样一个函数,可以根据高斯分布计算权重:
const float dx = 1.0f / static_cast<float>(points - 1);
const float sigma = 1.0f / 3.0f;
const float norm = 1.0f / (sqrtf(2.0f * static_cast<float>(M_PI)) * sigma);
const float divsigma2 = 0.5f / (sigma * sigma);
m_weights[0] = 1.0f;
for (int i = 1; i < points; i++)
{
float x = static_cast<float>(i)* dx;
m_weights[i] = norm * expf(-x * x * divsigma2) * dx;
m_weights[0] -= 2.0f * m_weights[i];
}
在以上所有计算中,数字并不重要。唯一重要的是m_weights[0] = 1.0f;
,每次我计算m_weights[i]
时,我都会像这样从m_weights[0]
中减去两次:
m_weights[0] -= 2.0f * m_weights[i];
以确保CCD_ 4将与CCD_。但事实并非如此。此断言失败:
float wSum = 0.0f;
for (size_t i = 0; i < m_weights.size(); ++i)
{
float w = m_weights[i];
if (i == 0) {
wSum += w;
} else {
wSum += (w + w);
}
}
assert(wSum == 1.0 && "Weights sum is not 1.");
如何确保所有平台上的总和为1.0f
?
你不能。浮点不是那样的。根据使用的cpu,即使添加相同的值也会产生不同的结果。
您所能做的就是定义一些精度值,并确保最终得到1.0+/-该值。
请参阅:http://docs.oracle.com/cd/E19957-01/806-3568/ncg_goldberg.html
因为浮点运算的精度只有23位(例如。https://en.wikipedia.org/wiki/Single-precision_floating-point_format),舍入误差会迅速累积,因此即使其余代码都是正确的,你的和也会变成1.0000001或0.9999999(顺便问一下,你有没有在调试器中看过它,或者试图将它打印到控制台?)。为了提高精度,您可以将float替换为double,但总和仍不完全是1.0:误差会更小,类似于1e-16而不是1e-7。第二件事是用范围比较来代替与1.0的严格比较,比如:
assert(fabs(wSum - 1.0) <= 1e-13 && "Weights sum is not 1.");
这里,1e-13是ε,在ε内,两个浮点数相等。如果你选择float(而不是double),你可能需要类似1e-6的epsilon。
根据权重的大小和点数的多少,累积误差可能会大于ε。在这种情况下,您需要特殊的算法来保持更高的精度,例如在从最小的数字开始求和之前,根据数字的绝对值对数字进行排序。
如何确保所有平台上的总和为1.0f?
正如其他答案(和评论)所说,由于浮点计算的不精确性,您无法实现这一点。
一种解决方案是,不使用double
,而是使用定点或多精度库,如GMP、Boost Multiprecision library或其他许多库中的一个。
- 正在查找文档以获得PS4平台的C++中的设备信息
- D3D11-将混合权重和索引传递到顶点着色器
- C/C++ - 查询平台相关的换行符(用于内存映射文件)
- 提升如何在图形可视化中写入边缘的权重?
- 如何基于平台在制作文件中制作if语句?
- 在 Linux 平台的 C++ 中动态加载 DLL
- 无法使用 aarch64-unknown-nto-qnx7.0.0-g++-5.4.0 编译器交叉编译 QNX 平台的
- 如何判断类型双关语在我的平台上是否可以?
- 如何使用可视化代码和平台IO将环境变量注入CPP文件?
- 如何实现具有多个平台__FILE__和__LINE__信息的 C/C++ 可变参数日志记录宏?
- 操作系统平台支持宏和提升库
- 平台游戏 - 下车时避免与平台碰撞
- NPM 安装:找不到平台工具集 = v141
- OpenCV 3 中的神经网络权重
- 如何在 64 位平台上计算 32 位哈希C++?
- 我的代码在不同的平台上给出不同的输出
- 是否有任何 2 补充平台/编译器,其中有符号移位不做通常的事情?
- 哪些 C++ 数据类型是 Metal 和所有其他 C++ 平台共有的
- 如何创建独立于平台的宏来包装编译器扩展?
- 多平台库设计.最佳实践