scalacheck中的大型发电机

Jer*_*iho 15 scala scalacheck

UserGuide scalacheck项目的提到大小的发电机.解释代码

def matrix[T](g:Gen[T]):Gen[Seq[Seq[T]]] = Gen.sized {size =>
 val side = scala.Math.sqrt(size).asInstanceOf[Int] //little change to prevent compile-time exception
 Gen.vectorOf(side, Gen.vectorOf(side, g))
}
Run Code Online (Sandbox Code Playgroud)

没有为我解释.经过一番探索后,我了解到生成序列的长度并不依赖于生成器的实际大小(Gen对象中的resize方法根据javadoc"创建生成器的大小调整版本"(也许这意味着不同的东西?)).

val g =  Gen.choose(1,5)
val g2 = Gen.resize(15, g)
println(matrix(g).sample) //  (1)
println(matrix(g2).sample) // (2)
//1,2 produce Seq with same length 
Run Code Online (Sandbox Code Playgroud)

你能解释一下我错过了什么,并举例说明你如何在测试代码时使用它们?

Ric*_*son 19

vectorOf(其现在被替换为listOf具有大小取决于(线性地)上ScalaCheck集时它的计算结果的发电机的尺寸参数)生成列表.当ScalaCheck测试属性时,它将为每个测试增加此大小参数,从而产生使用越来越大的列表(如果listOf使用)进行测试的属性.

如果通过仅以listOf嵌套方式使用生成器来创建矩阵生成器,则将获得具有取决于size参数的平方的大小的矩阵.因此,当在属性中使用这样的生成器时,您可能会得到非常大的矩阵,因为ScalaCheck会增加每次测试运行的大小参数.但是,如果您resize按照ScalaCheck用户指南中的方式使用生成器组合器,则最终的矩阵大小将与size参数线性相关,从而在测试属性时获得更好的性能.

你应该不必resize经常使用发电机组合器.如果你需要生成以某个特定大小为界的列表,那么更好的做法就像下面的例子那样,因为不能保证listOf/ containerOfgenerator确实按照你期望的方式使用size参数.

def genBoundedList(maxSize: Int, g: Gen[T]): Gen[List[T]] = {
  Gen.choose(0, maxSize) flatMap { sz => Gen.listOfN(sz, g) }
}
Run Code Online (Sandbox Code Playgroud)


Arj*_*ijl 11

vectorOf不推荐使用您使用的方法,您应该使用listOf方法.这将生成随机长度列表,其中最大长度受发生器大小的限制.因此,如果要控制生成的最大元素,则应调整实际生成实际列表的生成器的大小:


scala> val g1 = Gen.choose(1,5)
g1: org.scalacheck.Gen[Int] = Gen()

scala> val g2 = Gen.listOf(g1)  
g2: org.scalacheck.Gen[List[Int]] = Gen()

scala> g2.sample
res19: Option[List[Int]] = Some(List(4, 4, 4, 4, 2, 4, 2, 3, 5, 1, 1, 1, 4, 4, 1, 1, 4, 5, 5, 4, 3, 3, 4, 1, 3, 2, 2, 4, 3, 4, 3, 3, 4, 3, 2, 3, 1, 1, 3, 2, 5, 1, 5, 5, 1, 5, 5, 5, 5, 3, 2, 3, 1, 4, 3, 1, 4, 2, 1, 3, 4, 4, 1, 4, 1, 1, 4, 2, 1, 2, 4, 4, 2, 1, 5, 3, 5, 3, 4, 2, 1, 4, 3, 2, 1, 1, 1, 4, 3, 2, 2))

scala> val g3 = Gen.resize(10, g2)
g3: java.lang.Object with org.scalacheck.Gen[List[Int]] = Gen()

scala> g3.sample
res0: Option[List[Int]] = Some(List(1))

scala> g3.sample
res1: Option[List[Int]] = Some(List(4, 2))

scala> g3.sample
res2: Option[List[Int]] = Some(List(2, 1, 2, 4, 5, 4, 2, 5, 3))
Run Code Online (Sandbox Code Playgroud)