有没有方便的方法对多个数据集执行测试 - 比如JUnit的参数化测试?
答案 0 :(得分:10)
有一项新功能可用于测试ScalaTest 1.5中的多个数据集,您现在可以将其作为快照进行尝试。它发布在scala-tools.org:
组ID:org.scalatest artifact id:scalatest 版本:1.5-SNAPSHOT
您混合(或导入TableDrivenPropertyChecks的成员),然后您可以定义这样的表:
val examples =
Table(
("a", "b", "c", "d"),
( 1, 1, 1, 1),
( 1, 1, 1, 1),
( 1, 1, 1, 1),
( 1, 1, 1, 1)
)
将var元组的元组列表传递给Table。每个元组都必须具有相同的元素,在这种情况下,每个元组都有4个元素(4个成员)。第一个元组是所有字符串,它们定义列的名称。随后的元组每个都定义一行数据。您可以在元组中放置任何类型,但通常每列都包含相同的类型。虽然如果你想要你可以有任何类型的列可以包含任何东西。您可以拥有1到22列的表。如果您需要超过22列(Scala中的最大元组大小当前为22),您可以在一列或多列中使用复合类型。
一旦你有了一张桌子,就可以像这样检查它们:
forAll (examples) { (a, b, c, d) =>
a + b + c + d should equal (4)
}
forAll需要两个参数列表。第一个是表,第二个是“属性函数”,它表示对于表的每一行都应该为true的东西。 forAll将占用表的每一行(当然,跳过列名的标题行)并确保该属性成立。如果没有,则会收到一条错误消息,指出表中哪一行失败,指定列的值是什么等等。
表是数据元组的Seq,因此您也可以像Seq一样使用它。例如,您可以获得一个Seq of Option [Exception],指示哪些行失败如下:
for ((a, b, c, d) <- examples) yield {
failureOf { a + b + c + d should equal (4) }
}
结果Seq包含表中每行数据的一个选项,如果属性为该行传递,则为None;如果属性失败,则为[Exception]。 Some中的例外包含有关失败的所有细节。
答案 1 :(得分:6)
Shared tests对您来说很有趣。它们允许您定义一些测试集,如此堆栈示例中所示:
def nonEmptyStack(stack: Stack[Int], lastItemAdded: Int) {
"be non-empty" in {
assert(!stack.empty)
}
"return the top item on peek" in {
assert(stack.peek === lastItemAdded)
}
"not remove the top item on peek" in {
val size = stack.size
assert(stack.peek === lastItemAdded)
assert(stack.size === size)
}
"remove the top item on pop" in {
val size = stack.size
assert(stack.pop === lastItemAdded)
assert(stack.size === size - 1)
}
}
然后在实际规范中你可以像这样使用它:
behave like nonEmptyStack(stackWithOneItem, lastValuePushed)
因此换句话说, nonEmptyStack 是一组参数化测试,可以与您要测试的不同数据集一起使用。
答案 2 :(得分:4)
数据驱动测试的另一种可能性是使用以下语法:
class SampleTest extends FunSuite {
val input = List((1, 1), (4, 2), (9, 3))
input.foreach{i =>
test(s"Test of math.sqrt(${i._1})") {
assert(math.sqrt(i._1) === i._2)
}
}
}
默认情况下,测试并行执行,除非在build.sbt中设置parallelExecution in Test := false
。