1

我正在尝试为sGen[Stream[A]]的无限(延迟评估)流定义 a ,A其中每个元素A都可以依赖于先前的元素。

作为最小的情况,我们可以取下Gen[Stream[Int]]一个元素是前一个元素+1+2前一个元素的位置。这里是一个haskell实现供参考:

increasingInts :: Gen [Int]
increasingInts = arbitrary >>= go
  where
    go seed = do
      inc <- choose (1,2)
      let next = seed + inc
      rest <- go next
      return (next : rest)

我已经尝试Gen.sequenceStream[Gen[A]]但有一个stackoverflow。我也尝试Gen从头开始定义,但构造函数genGen私有的,并且适用于私有方法/类型。

这种尝试也给出了stackoverflow。

  def go(seed: Int): Gen[Stream[Int]] =
    for {
      inc <- Gen.choose(1, 2)
      next = seed + inc
      rest <- Gen.lzy(go(next))
    } yield next #:: rest

  val increasingInts: Gen[Stream[Int]] = go(0)


increasingInts(Gen.Parameters.default, Seed.random()).get foreach println

所以我被困住了。有任何想法吗?

4

1 回答 1

2

您可以通过以下方式实现您想要的:

val increasingInts = {
  val increments = Gen.choose(1, 2)
  val initialSeed = 0
  for {
    stream <- Gen.infiniteStream(increments)
  } yield stream.scanLeft(initialSeed)(_ + _)
}

.scanLeft就像 a.foldLeft但保留中间值,从而给你另一个Stream.


我在这里写过scanLefthttps ://www.scalailliam.com/most-important-streaming-abstraction/

于 2018-03-26T11:33:06.410 回答