java 为随机数生成器编写 JUnit 测试
声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow
原文地址: http://stackoverflow.com/questions/14811014/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me):
StackOverFlow
Writing a JUnit test for a random number generator
提问by Carrie Hall
I have a method which returns a random number between 0 and 10.
我有一个方法可以返回 0 到 10 之间的随机数。
public int roll(){
int pinsKnockedDown = (int) (Math.random() * 10);
return pinsKnockedDown;
}
How would I write a JUnit test for this? So far I have put the call in a loop so it runs 1000 times and fails the test if - the number is less than 0 - the number is more than 10
我将如何为此编写 JUnit 测试?到目前为止,我已将调用置于循环中,因此它运行了 1000 次,并且如果 - 数字小于 0 - 数字大于 10,则测试失败
How can I test that all the numbers aren't just the same, i.e.
我怎样才能测试所有的数字都不一样,即
采纳答案by Carrie Hall
My answer was already flawed, I needed to return a number from 0-10 but my original post only returned a range from 0-9! Here is how I found that out...
我的答案已经有缺陷,我需要返回一个 0-10 的数字,但我原来的帖子只返回了 0-9 的范围!这是我发现的方法...
Loop 100k times and make sure that the range is correct, it should be 0-10 (although I've set 10 as a variable so that the code can be re-used).
循环 100k 次并确保范围正确,它应该是 0-10(虽然我已经将 10 设置为变量以便代码可以重用)。
Also I store the highest and lowest values that were found during the loop and they shouldbe at the extreme ends of the scale.
我还存储了在循环过程中发现的最高和最低值,它们应该位于刻度的最末端。
If the highest and lowest values are the same then that's an indicator that someone has faked a random number return.
如果最高值和最低值相同,则表明有人伪造了随机数返回值。
The only problem that I see is that it is possibleto have a false negative from this test, but it is unlikely.
我看到的唯一问题是此测试可能会出现假阴性,但不太可能。
@Test
public void checkPinsKnockedDownIsWithinRange() {
int pins;
int lowestPin = 10000;
int highestPin = -10000;
for (int i = 0; i < 100000; i++) {
pins = tester.roll();
if (pins > tester.NUMBER_OF_PINS) {
fail("More than 10 pins were knocked down");
}
if (pins < 0) {
fail("Incorrect value of pins");
}
if (highestPin < pins) {
highestPin = pins;
}
if (lowestPin > pins) {
lowestPin = pins;
}
}
if (lowestPin == highestPin) {
fail("The highest pin count is the same as the lowest pin count. Check the method is returning a random number, and re-run the test.");
}
if (lowestPin != 0) {
fail("The lowest pin is " + lowestPin + " and it should be zero.");
}
if (highestPin != tester.NUMBER_OF_PINS) {
fail("The highest pin is " + highestPin + " and it should be " + tester.NUMBER_OF_PINS + ".");
}
}
回答by Brian Agnew
Randomness testsare potentially complex. e.g. in the above do you simply want to ensure you get numbers between 1 and 10 ? Do you want to ensure a uniform distribution etc.? At some stage I would suggest you want to trust Math.random()
and simply ensure you haven't screwed up the limits/range, which is essentially what you're doing.
随机性测试可能很复杂。例如在上面你只是想确保你得到 1 到 10 之间的数字吗?您想确保均匀分布等吗?在某个阶段,我建议您信任Math.random()
并确保您没有搞砸限制/范围,这基本上就是您正在做的事情。
回答by Raedwald
You want to test yourcode, not the quality of the Java supplied Math.random(). Assume the Java method is good. All tests are necessary but not sufficient conditions for correctness. So choose some tests that will uncover likely programming errors in use of the Java supplied method.
您想测试您的代码,而不是 Java 提供的 Math.random() 的质量。假设 Java 方法是好的。所有测试都是正确性的必要但不是充分条件。因此,请选择一些测试,以发现在使用 Java 提供的方法时可能存在的编程错误。
You might test the following: Eventually, after a succession of calls, the function returns each digit at least once, without returning any numbers out of the required range.
您可以测试以下内容: 最终,在连续调用之后,该函数至少返回每个数字一次,而不会返回任何超出所需范围的数字。