在Scala中,我可以执行以下操作:
abstract class MyData
case class A() extends MyData
case class B() extends MyData
implicit class HeavyComputationProvider(val data : MyData) {
private def _HeavyComputation() = /* */;
lazy val HeavyComputation = this._HeavyComputation();
}
// Example usage:
val a = A
println a.HeavyComputation // This will calculate
println a.HeavyComputation // This will use the cached value
重用时具有缓存的优势,但不使用时不进行缓存。
如何为以下F#类型提供惰性
HeavyComputation
?type MyData =
| A
| B
type MyData with
member private this.__HeavyComputation = (* *)
// Error: This declaration element is not permitted in an augmentation and this is unavailable
let _HeavyComputation = lazy((* *))
// This will just create a *new* lazy computation each time
member this._HeavyComputation = lazy(this.__HeavyComputation)
// This should lazily compute & cache, transparent to the caller
member this.HeavyComputation = this._HeavyComputation.Force
最佳答案
我认为没有直接等同于Scala方法的方法。为此,需要将一些其他状态保留为对象的一部分(例如,惰性值),并且一旦定义了对象,F#便不允许您向对象添加其他状态。
您可以做的最接近的事情是编写一个包装器类型,将原始MyData
值与其他惰性计算一起存储:
type MyData =
| A
| B
type MyDataWithComputation(data:MyData) =
let _HeavyComputation = lazy(1)
member this.MyData = data
member this.HeavyComputation = _HeavyComputation.Value
然后按如下方式使用它:
let myd = MyDataWithComputation(A)
myd.HeavyComputation
myd.HeavyComputation