什么是处理永远不会进入的开关盒的最合适的方法?

时间:2016-01-08 02:52:53

标签: c++ switch-statement c++03 control-flow

以下是我的代码的一些部分:

enum Mode {
    MAIN = 0,
    NUM_GEN,
    ARITH,
    MONEY,
    END_FLAG
}

int main() {
    launchModule(MAIN);

    return 0;
}

void launchModule(Mode mode) {
    ...
    getline(cin, input);
    choice = stoi(input);
    // More input validation

    switch (mode) {
    case MAIN:
        switch (static_cast<MODE>(choice)) {
        // Other cases: Recursively calls launchModule(choice)
        case END_FLAG:
            // Exits current function
            break;
        }
        break;
    // Other cases: no switch(Mode) happens
    case END_FLAG:
    // TODO: What goes here?
        break;
    }
    ...
    return;
}

如上所述,launchModule(mode)首先使用输入main()调用MAIN,并且可以使用ModeEND_FLAG之外的任何值递归调用自身。因此,可以说launchModule永远不会被输入值END_FLAG调用。尽管如此,case END_FLAG存在于第一个switch语句块中,应该以某种方式处理。一般来说,处理switch语句中永远不会输入的案例的适当方法是什么?

这里可以假设这些是调用launchModule()时的唯一实例。

1 个答案:

答案 0 :(得分:4)

鉴于它永远不应该被输入,适当的响应可能是使用适当的错误消息抛出异常,断言或中止执行。

在这些之间进行选择可能非常重要。当您使用NDEBUG进行编译时,将禁用断言,您可能不需要。否则,它立即中止程序(不调用析构函数等)。当你想在调试时快速终止程序时,这往往会使它最合适,但可能(例如)记录并继续在已发布的代码中执行。

如果可能从此错误中恢复,抛出异常将是最合适的,尤其是对于必须继续执行的服务器代码,无论发生什么事情。

如果您确定这是一个真正致命的错误,只有在某些事情发生了可怕的错误时才会中止,并且尝试在此时继续执行可能会破坏数据,因此您希望退出尽可能快速和吵闹(特别是,你要确保防止析构函数运行,因为它们可能会使情况更糟糕)。

在这里给出的情况下,如果输入switch语句的这一段,代码内部就会出现明显的问题。这表明至少通常你会在断言或自己中止之间做出选择。我倾向于后者,因为你可能不想在发布的代码中禁止这种行为。