Performance 填充一个列表是Scala的一个永久性随机双精度运算
我是Scala新手,正在尝试获取随机双精度值列表: 问题是,当我尝试运行它时,它比它的Java对应程序花费的时间太长了。有没有关于这是为什么的想法,或者关于更有效的方法的建议Performance 填充一个列表是Scala的一个永久性随机双精度运算,performance,list,scala,Performance,List,Scala,我是Scala新手,正在尝试获取随机双精度值列表: 问题是,当我尝试运行它时,它比它的Java对应程序花费的时间太长了。有没有关于这是为什么的想法,或者关于更有效的方法的建议 def random: Double = java.lang.Math.random() var f = List(0.0) for (i <- 1 to 200000) ( f = f ::: List(random*100)) f = f.tail def random:Double=java.lang.
def random: Double = java.lang.Math.random()
var f = List(0.0)
for (i <- 1 to 200000)
( f = f ::: List(random*100))
f = f.tail
def random:Double=java.lang.Math.random()
var f=列表(0.0)
对于(i,您可以构造无限个随机双精度流:
def randomList(): Stream[Double] = Stream.cons(math.random, randomList)
val f = randomList().take(200000)
这将利用延迟求值,因此在实际需要之前,您不会计算值。尽管如此,即使求值全部200000也会很快。作为额外的好处,
f
不再需要是一个var
,如果您使用可变状态,您应该使用一个可变集合,如缓冲区,您也可以使用+=
(这将是java代码的真正对应项)
但是你为什么不使用列表理解呢
val f = for (_ <- 1 to 200000) yield (math.random * 100)
val f=for(p>另一种可能性是:
val it = Iterator.continually(math.random)
it.take(200000).toList
Stream
也有一个连续
方法,如果您愿意的话。您也可以这样实现:
List.fill(200000)(math.random)
这同样适用于例如数组
Array.fill(200000)(math.random)
等等…还有更多选项!尾部递归:
def randlist(n: Int, part: List[Double] = Nil): List[Double] = {
if (n<=0) part
else randlist(n-1, 100*random :: part)
}
首先,它不会比java花费更长的时间,因为没有java对应物。java没有一个不变的列表。如果它有,性能将大致相同
其次,它需要很多时间,因为附加列表具有线性性能,所以整个过程具有二次性能
不是追加,而是预结束,它具有恒定的性能。看起来您想使用Vector而不是List。List有O(1)个预结束,Vector有O(1)个追加。由于您是追加,但使用的是串联,所以使用Vector会更快:
def random: Double = java.lang.Math.random()
var f: Vector[Double] = Vector()
for (i <- 1 to 200000)
f = f :+ (random*100)
def random:Double=java.lang.Math.random()
变量f:Vector[Double]=Vector()
对于(i)使用:::以这种方式,每次迭代都要重建整个列表。理想情况下,实际上应该使用惰性数据结构,但如果确实需要列表,请使用f=(random*100)::f
也可以从var f:list[Double]开始=Nil
-不需要定义random,只需导入它:导入java.lang.Math.random
顺便说一句,java.lang.Math.random()
不是特别随机的(请参见:)。一个好的选择(还有其他选择)是。还有一个scala.util.Random
,不需要使用Java版本。@Jesper:是的。但是应该注意的是scala.util.Random
只是Java.util.Random()
的包装器。一个小的调整:val f=for(uuu感谢马丁,非常简洁明了的替代品。嘿,谢谢马丁,但我注意到了关于这个替代品的一些东西——如果我试图把这个名单传给一个演员,那就要花很长时间(超过20个替身的名单)-但是我的原始代码没有超过20码的列表。谢谢伯恩先生,你知道我为什么会死得这么惨吗?我想这是因为:::导致每次都生成一个新的列表,从而成为cpu上的杀手?是的,你是对的。你每次迭代都在重建整个列表。使用math.random
,这就是answer我会给:)@Kevin:当然。改变了。我的借口是我通常用a来代替,不管怎样……这是一种标新立异的方式,“标新立异”是我创造的一个词,意思是“符合公认的标新立异习语”,与“Pythonic”平行,这是对任何被欣然接受的替代词的提名。@Malvolio:怎么样“Scalar?”:)@Malvolio:我指定“Scalaric”如果你的随机数倒过来真的很重要吗?谢谢。序列并不重要(在我的例子中),因为它们都将被传递给参与者进行选择排序。
def random: Double = java.lang.Math.random()
var f: Vector[Double] = Vector()
for (i <- 1 to 200000)
f = f :+ (random*100)