如何在C#中使用以特定间隔分隔的数字初始化数组

我想创建一个包含从0到1的值的数组,间隔为0.1。 我可以用:

float[] myArray = new float[10]; float increment = 0.1; for(i = 0; i < 10; i++) { myArray[i] = increment; increment += 0.1; } 

我想知道是否有像Enumerable.Range这样的函数允许指定增量间隔。

一个有趣的事实是,到目前为止发布的每个答案都修复了您提议的代码中的错误 ,但只有一个人已经说过他们已经这样做了。

当处理任何不是精确2的幂的一小部分的数量时,二进制浮点数具有表示错误 。 (“3.0 / 4.0”是可表示的分数,因为底部是2的幂;“1.0 / 10.0”不是。)

因此,当你说:

 for(i = 0; i < 10; i++) { myArray[i] = increment; increment += 0.1; } 

实际上你并没有将“增量”增加1.0 / 10.0。 您将通过底部具有精确幂2最接近的可表示分数递增它。 所以实际上这相当于:

 for(i = 0; i < 10; i++) { myArray[i] = increment; increment += (exactly_one_tenth + small_representation_error); } 

那么, 第十个增量的价值是多少? 显然它是10 * (exactly_one_tenth + small_representation_error) ,它显然等于exactly_one + 10 * small_representation_error您已将表示错误的大小乘以10。

每次重复将两个浮点数加在一起时, 每次后续添加都会略微增加总和的总表示误差,并且实际上会增加一个潜在的大错误。 在某些情况下,您要汇总数千或数百万个小数字,误差可能会远远大于实际总数

更好的解决方案是做其他人所做的事情。 每次从整数重新计算分数 。 这样每个结果都有自己的小表示错误; 它不会累积先前计算结果的表示错误。

丑,但……

 Enumerable.Range(0,10).Select(i => i/10.0).ToArray(); 

不,没有可以允许你这样做的可数范围,但你可以总是除以10:

 foreach (int i in Enumerable.Range(0, 10)) array[i] = (i + 1) / 10.0f 

请注意,这可以避免在重复求和0.1f时累积的错误。 例如,如果在示例代码中对myArray中的10个元素求和,则得到的值比5.5更接近5.50000048。

这是一种方式:

 Enumerable.Range(1,10).Select(i => i /10.0) 

那你可以用这个:

 Enumerable.Range(1,10).Select(x => x / 10.0).ToArray() 

不确定这是否更好。