确定异常是否可重新抛出

时间:2012-09-02 10:24:33

标签: c# exception-handling

我有两个功能:

public void WithdrawMoney()
{
    //Take money from bank account
    //Exceptions abort the operation and are printed
    //Rethrow exception if called by TransferMoney()
}

public void TransferMoney()
{
    //Take money from one account and only deposit on another account if no exceptions were caught in WithdrawMoney()
    WithdrawMoney(); 
    DepositMoney();     
}

我想要的是能够重新抛出 WithdrawMoney()中发生的异常,只有当 TransferMoney()调用它时。如果我只是想从账户中提取资金,必须处理该例外情况,但不必重新抛出,因为它没有被其他方法调用。

除了使用bool之外,我还会想到另一种解决方案。我可以查看堆栈跟踪,看看 TransferMoney()是否称为 WithdrawMoney(),只有重新抛出异常(如果有)。或者有没有办法查看方法中是否发生异常?

我只想知道你是否可以在抛出之前检查一个异常是否可以在catch块中抛出。如果我总是抛出它,当我直接调用 WithdrawMoney()时,异常将无法处理。

4 个答案:

答案 0 :(得分:4)

由于某些难以理解和记录的任意条件,方法的行为不应该不同。

你应该重构你想要在内部使用的提款方法的一部分,这样你就可以从外部使用一种方法,从内部使用一种方法。

private void MakeWithdrawal() {
    //Take money from bank account
    //Exceptions abort the operation
}

public void WithdrawMoney()
{
    MakeWithdrawal();
    //Exceptions are printed
}

public void TransferMoney()
{
    //Take money from one account and only deposit on another account if no exceptions were caught in WithdrawMoney()
    MakeWithdrawal();
    DepositMoney();     
    //Exceptions are printed
}

答案 1 :(得分:3)

只需添加一个包装器。 Single Responsible 也适用于方法。

private void WithdrawMoney()
{
    // Take money from bank account

    // _Always_ Rethrow 
}

public void WithdrawMoneyPublic()
{
   // call WithdrawMoney and handle the exceptions
}

答案 2 :(得分:2)

您可以考虑在函数调用中添加可选参数:

public void WithdrawMoney(bool throwOnError = false)
{
    //Do stuff
    catch(Exception ex)
    {
        if(throwOnError) throw;
    } 
    //Do stuff
}

public void TransferMoney()
{
    WithdrawMoney(true);
}

但是,这是从“框架设计指南”中取出的,作为您不应编写的代码示例。这是一本很好的书。

答案 3 :(得分:1)

为什么要例外?

为什么你不让(甚至两种)方法返回bool,表明成功?

这听起来像你有bool的想法,但由于某种原因没有去做。为什么不呢?这是如此合乎逻辑和简单!

提取资金处理内部异常并返回false,TransferMoney将检查并返回false。您希望这些操作返回操作是否成功也是非常合乎逻辑的。

public bool WithdrawMoney()
{
    //Take money from bank account

    //Exceptions abort the operation and are printed, and return false

    //Flawless run returns true
}

public bool TransferMoney()
{
    //Take money from one account and only deposit
    //    on another account if WidthdrawMoney returned true
    if (WithdrawMoney())
    {
        DepositMoney();     
        return true;
    }

    return false;
}

毕竟 - 我会说你还需要检查第二次WithdrawMoney操作没有失败,如果确实如此 - 回滚你用第一次WithdrawMoney完成的更改。