我正在尝试在[numBins
,lower
范围内创建一个均匀分布的upper
个数字列表。当然,存在浮点问题,这种方法并不是最好的。然而,使用Range.Double
的结果让我感到惊讶,因为缺少的元素根本不接近上限。
设定:
val lower = -1d
val upper = 1d
val numBins = 11
val step = (upper-lower)/numBins // step = 0.18181818181818182
问题:
scala> Range.Double(lower, upper, step)
res0: scala.collection.immutable.NumericRange[Double] = NumericRange(-1.0, -0.8181818181818182, -0.6363636363636364, -0.45454545454545453, -0.2727272727272727, -0.0909090909090909, 0.09090909090909093, 0.27272727272727276, 0.4545454545454546, 0.6363636363636364)
问题:列表似乎是一个简短的元素。 0.8181818181818183更进一步,并且小于1.
解决方法:
Scala> for (bin <- 0 until numBins) yield lower + bin * step
res1: scala.collection.immutable.IndexedSeq[Double] = Vector(-1.0, -0.8181818181818181, -0.6363636363636364, -0.4545454545454546, -0.2727272727272727, -0.09090909090909083, 0.09090909090909083, 0.2727272727272727, 0.4545454545454546, 0.6363636363636365, 0.8181818181818183)
此结果现在包含预期的元素数,包括0.818181 ..
答案 0 :(得分:1)
我认为问题的根本原因是toString
NumericRange
的实施中的一些功能
217 override def toString() = {
218 val endStr = if (length > Range.MAX_PRINT) ", ... )" else ")"
219 take(Range.MAX_PRINT).mkString("NumericRange(", ", ", endStr)
220 }
UPD:不是toString
。其他一些方法(如map
和foreach
)会从返回的集合中剪切最后一个元素。
无论如何,通过查看您已收集的size
收藏集 - 您会发现 - 所有元素都在那里。
您在解决方法示例中所做的工作 - 使用了不同的基础数据类型。