我正在尝试计算浮动数组的平均值。我需要使用索引,因为它在二进制搜索中,因此顶部和底部将移动。(大图,我们正在尝试优化半程估计,因此我们不必在每次通过时都重新创建阵列)。
无论如何,我编写了一个自定义的平均循环,与c#Average()方法相比,我得到的精度低2位
float test = input.Average();
int count = (top - bottom) + 1;//number of elements in this iteration
int pos = bottom;
float average = 0f;//working average
while (pos <= top)
{
average += input[pos];
pos++;
}
average = average / count;
Run Code Online (Sandbox Code Playgroud)
例:
0.0371166766-C# 0.03711666-我的循环 125090.148-C# 125090.281-我的循环
我得到的位置比c#平均()低2位
不,您只损失1个有效数字。浮动类型只能存储7个有效数字,其余的只是随机噪声。不可避免地,在这样的计算中,您可能会累积舍入误差,从而导致精度下降。要使舍入错误平衡,需要运气。
避免这种情况的唯一方法是使用精度更高的浮点类型来累加结果。没问题,您有双重机会。这就是Linq Average方法看起来像这样的原因:
public static float Average(this IEnumerable<float> source) {
if (source == null) throw Error.ArgumentNull("source");
double sum = 0; // <=== NOTE: double
long count = 0;
checked {
foreach (float v in source) {
sum += v;
count++;
}
}
if (count > 0) return (float)(sum / count);
throw Error.NoElements();
}
Run Code Online (Sandbox Code Playgroud)
使用double可以复制Linq结果,并在结果中具有相当数量的有效数字。