写在Haskell时间函数(Writing a time function in Haskell)

2019-08-17 06:52发布

我是新来的Haskell和我希望能够在给定时间的函数调用或代码段的运行时间。

在Clojure中,我可以用“ 时间 ”:

user=> (time (apply * (range 2 10000)))
"Elapsed time: 289.795 msecs"
2846259680917054518906413212119868890148051...

在Scala中,我可以定义自己的功能:

scala> def time[T](code : => T) =  {
     |   val t0 = System.nanoTime : Double
     |   val res = code
     |   val t1 = System.nanoTime : Double
     |   println("Elapsed time " + (t1 - t0) / 1000000.0 + " msecs")
     |   res
     | }
time: [T](=> T)T

scala> time((1 to 10000).foldLeft(1:BigInt)(_*_))
Elapsed time 274.292224 msecs
res0: BigInt = 284625968091705451...

我怎么能写我的斯卡拉功能或Clojure的哈斯克尔“时间”的相同呢? 该System.TimeIt模块 ,因为它只有在要测量的IO计算的工作,我就发现Hackage不够普遍。 所以timeIt(4 + 4)是行不通的,只有timeIt(print $ 4 + 4)这很烦人的快。 除此之外,我真的希望看到哈斯克尔是如何处理的一般情况。

谢谢!

Answer 1:

请看为此使用标准库:

  • 在Haskell时序计算
  • 准则 ,可能最好的开源标杆/定时在存在库
  • 关于标准

只需使用标准。


在评价深度的说明 :懒惰意味着你需要决定你要多少评价你的时间运行期间有。 通常你会想,以减少你的代码到正常形态。 该NFData类型类,您可以通过RNF方法做到这一点。 如果评估到最外层构造是确定的,使用seq上的纯代码,迫使其评价。



Answer 2:

Haskell是懒洋洋地评估。 如果您的表达式不具有一定的副作用(如编码在IO单子等),则该程序并不需要真正解决这个表达式的值,因此不会。

为了得到有意义的数字了这一点,你可以尝试定时print 4print expr和走差异化,以去除字符串格式化和IO的开销。



Answer 3:

懒人懒手段。 时间仅在相关IO一样单子里面。

时间在表达“4 + 4”没有意义 - 或任何其他数学方程。 答案简单地说就是。 “答案”到任何其他的纯计算已经预定被指定的计算的瞬间。

不幸的是,这是“答案”你的问题。 ,其实,你之前就已经存在的答案,甚至提出你的问题。 它在1998年时存在语言终于确定。 我花了一年的时间写这并不重要事实;-)

OK,足够的废话!!!! (但是,如果上面是太烦人了,然后就忘了哈斯克尔。)

如果该标准包是太痛了,只写一个测试用例,并使用+ RTS进行测试。

如果你想成为真的很酷,创建自己的单子 - 一个时代你的算法和手的结果与算法的返回值回tupled执行。 祝好运。 我们都指望你了!



文章来源: Writing a time function in Haskell