Scala 记住收缩时的这些条款

Scala 记住收缩时的这些条款,scala,scalacheck,Scala,Scalacheck,如果我有一个自定义生成器,则收缩器将记住我的等子句,并且不会使用无效值进行收缩: val myGen = Gen.identifier.suchThat { _.length > 3 } // all shrinks have > 3 characters property("failing case") = forAll (myGen) { (a: String) => println(s"Gen suchThat Value: $a") a == "Impossi

如果我有一个自定义生成器,则收缩器将记住我的
子句,并且不会使用无效值进行收缩:

val myGen = Gen.identifier.suchThat { _.length > 3 }

// all shrinks have > 3 characters
property("failing case") = forAll (myGen) { (a: String) =>
  println(s"Gen suchThat Value: $a")
  a == "Impossible"
}
如果我对生成的值做了进一步的操作(即映射),那么收缩器将“忘记”我的此类子句:

// the shrinker will shrink all the way down to ""
property("failing case") = forAll (myGen.map{_ + "bbb"}) { (a: String) =>
    println(s"Gen with map Value: $a")
    a == "Impossible"
}

是否有可能使这些值通过生成器传播。在我真正的项目中,我所做的不仅仅是一张简单的地图,但这似乎是我遇到的限制的最简单的例子。

我相当肯定答案是否定的(至少在这个时候)

这是相当烦人的,尽管可能不像看上去那么琐碎。生成器结果确实尝试跟踪筛选,尽管它在
map
flatMap
中丢失。除了对收缩的结果应用筛子外,没有任何其他连接返回到发电机。即使存在所有中间结果,也需要保留并应用于每个筛子的正确点。这就引出了一个问题:究竟是什么在缩水?生成的结果或原始生成器

到目前为止,我找到的唯一解决方案是:

  • 禁用收缩,或
  • 实施自定义的
    收缩
    ,或
  • 添加重新检查生成值的
    where
    子句
这可能非常具有挑战性,尤其是在组合多个生成器时