【发布时间】:2013-03-09 22:36:29
【问题描述】:
我正在测试一种引发两种不同异常的方法。这是我的标题:
@Test (expected = A8InvalidInputException.class)
public void testGuessCharacter() throws A8InvalidInputException, A8AlreadyGuessedException
{
...
}
主体有两个 try/catch 块(对 SO 的搜索会导致一篇帖子说这是您测试抛出异常的方式),一个用于每个异常。在我看来,我应该把它分成两种测试方法,特别是因为我只能有一个 expected 属性。但是,当我这样做时,应该测试 A8InvalidInputException 的方法需要 A8AlreadyGuessedException 的 try/catch,而应该测试 A8AlreadyGuessedException 的方法需要 A8InvalidInputException 的 try/catch。我不确定如何编写这个测试。这是我正在尝试测试的方法:
/**
* This method returns whether a specified character exists in the keyPhrase field
* @param guess a character being checked for in the keyPhrase field
* @return returns whether a specified character exists in the keyPhrase field
* @throws A8InvalidInputException if a non-valid character is passed as input to this method
* @throws A8AlreadyGuessedException if a valid character which has already been guessed is passed as input to this method
*/
public boolean guessCharacter(char guess) throws A8InvalidInputException, A8AlreadyGuessedException
{
if(isValidCharacter(guess))
{
guess = Character.toLowerCase(guess);
if(guessedCharacters.contains(guess) )
{
throw new A8AlreadyGuessedException("" + guess);
}
else
{
guessedCharacters.add(guess);
if(keyPhrase.contains("" + guess))
return true;
else
{
numberOfGuessesLeft--;
return false;
}
}
}
else
{
throw new A8InvalidInputException("" + guess);
}
}
【问题讨论】:
-
反正方法太长了。
-
戴夫,我的导师提供了。我没写。除此之外,根据 Java 编码指南/样式指南,我认为 30 行是业界公认的最大值。
-
"行业接受的最大值?"从来没有听说过这样的事情。更重要的是,它具有足够高的圈复杂度,让我感到抽搐:条件嵌套太深而无法方便推理,并且在不需要的地方嵌套。重复的逻辑,因为当其他一切都需要一个字符串时有一个字符。简单的扁平化(大约gist.github.com/davelnewton/258761cbf3143da4288c)解决了这个问题。适当的重构使测试变得如此微不足道,几乎变得有趣。
-
嗯,测试是为了练习,所以一点也不复杂。我有另一位讲师教我们在将输入作为参数传递之前验证输入。它变得令人困惑。
-
发生数据验证的位置在很大程度上无关紧要。但你错了;该方法处于圈复杂度的上限(10 是典型的默认最大值;我在 ~5 左右感到抽搐)。方法应该做一件事,并且完全做到。这种方法明显不止一件事,增加了认知负荷而没有相应的好处。因此,测试变得更加困难。
标签: java exception junit junit4