如何避免使用try ... catch块

rya*_*dlf 5 java try-catch

我理解这些是必要的......当然要编写正确的代码,但是有没有一种设计模式可以帮助避免在类中重复尝试... catch块?例如,我编写了一个抛出5个不同异常的特定类.

public void iterateComparatorResults(ArrayList<ComparatorValue> results) throws IOException, IllegalArgumentException, IntrospectionException, IllegalAccessException, InvocationTargetException {
    Iterator<ComparatorValue> iterator = results.iterator();
    for(int i=0; i<results.size(); i++) {
        //Set data variables.
        setBeans(results.get(i).getClientBean(), results.get(i).getServerBean());
        setValues(results.get(i).getClientValue(), results.get(i).getServerValue());

        if(results.get(i).isMatch()) {
            //Data matches.
            runIteratorTrueAction();
        } else if(results.get(i).getInnerBeans() != null){
            //Value is a nested bean. Iterate again.
            ArrayList<ArrayList<ComparatorValue>> innerResults = results.get(i).getInnerBeans();
            for(int r=0; r<innerResults.size(); r++) {
                iterateComparatorResults(innerResults.get(r));
            }

        } else {
            //Data does not match.
            runIteratorFalseAction();
        }
    }
}
Run Code Online (Sandbox Code Playgroud)

每次我引用这个特定的方法是任何其他类,我必须使用看起来像这样的try catch块.

try {
    beanComparator.setIteratorFalseAction(falseAction);
                beanComparator.iterateComparatorResults(beanComparator.compareBeans(contact, compareContact));
} catch (IllegalArgumentException e) {
    e.printStackTrace();
} catch (IOException e) {
    e.printStackTrace();
} catch (IntrospectionException e) {
    e.printStackTrace();
} catch (IllegalAccessException e) {
    e.printStackTrace();
} catch (InvocationTargetException e) {
    e.printStackTrace();
}
Run Code Online (Sandbox Code Playgroud)

我希望有一些我可以实现的设计模式,所以我可以创建一个单独的类或其他东西,并在一个地方隐藏所有的try块然后引用该类并使用try块而不必实际编写它们.类似于像Spring这样的其他框架的方式吗?我只是需要一点指示如何做到这一点,因为我甚至不知道从哪里开始.

Mic*_*tta 8

我不确定你的例子是多么现实,但是没有必要a)分别捕获每个异常,如果你不区别地处理它们,或者b)在许多情况下捕获它们.

您在示例中所做的只是打印堆栈跟踪,几乎在所有情况下都是一个坏主意.你将凌乱的信息打印到一个没人注意的地方.

我遵循两个一般准则:

  1. 如果可以的话,处理抛出它的异常(例如,关闭文件访问异常中的打开文件,或重试麻烦的接口(愚蠢的不可靠的定制USB设备......)).
  2. 允许异常冒泡到堆栈中更高的位置,您可以捕获所有无法处理的异常.记录它们,显示它们或杀死你的应用程序,无论什么是最有意义的.

我将用一些代码说明第二点,这些代码是在Java教程的启发下窃取的.

private String readFirstLineFromFile(String path) throws IOException
{
    try (BufferedReader br = new BufferedReader(new FileReader(path)))
    {
        return br.readLine();
    }
}
Run Code Online (Sandbox Code Playgroud)

在这里,我们定义了一种尝试从文件中读取的方法.这里有很多东西可能会出错,但是这个级别的代码没有什么可以做的.相反,它将使用该throws子句将调用传递给调用它的方法.该调用方法可以处理异常本身,或者使用相同的子句将buck传递给它的调用者:

private String readAllTheFiles() throws IOException
{
    for (...)
    {
        readFirstLineFromFile(...);
    }
}
Run Code Online (Sandbox Code Playgroud)

现在,关于 Java throws在这种情况下需要的原因有很多争论.许多其他语言不会使用它们,无论好坏.您经常会看到RuntimeExceptions- 不需要throws子句的异常.如果你的方法可能会引发从延伸的例外RuntimeException,你并不需要声明的事实的throws.


Ran*_*Rag 5

如果您使用 JDK-7,您可以像这样包装 catch 块

catch (NoSuchMethodException | IllegalAccessException | InvocationTargetException e) {
e.printStackTrace();
} 
Run Code Online (Sandbox Code Playgroud)