8

假设我有以下功能:

Thingy& getThingy(int id)
{
    for ( int i = 0; i < something(); ++i )
    {
        // normal execution guarantees that the Thingy we're looking for exists
        if ( thingyArray[i].id == id )
            return thingyArray[i];
    }

    // If we got this far, then something went horribly wrong and we can't recover.
    // This function terminates the program.
    fatalError("The sky is falling!");

    // Execution will never reach this point.
}

编译器通常会对此抱怨,说“并非所有控制路径都返回值”。这在技术上是正确的,但是不返回值的控制路径会在函数结束之前中止程序,因此在语义上是正确的。有没有办法告诉编译器(在我的情况下是 VS2010,但我也对其他人感到好奇)为了进行此检查而忽略某个控制路径,而不会完全抑制警告或返回无意义的假人函数末尾的值?

4

3 回答 3

12

您可以注释函数fatalError(它的声明),让编译器知道它永远不会返回。

在 C++11 中,这将类似于:

[[noreturn]] void fatalError(std::string const&);

在 C++11 之前,您具有编译器特定的属性,例如 GCC:

void fatalError(std::string const&) __attribute__((noreturn));

或 Visual Studio 的:

__declspec(noreturn) void fatalError(std::string const&);
于 2012-08-27T17:42:37.093 回答
2

为什么不抛出异常?这将解决问题,并强制调用方法处理异常。

如果你确实设法以某种方式讨价还价,你仍然不得不对调用 getThingy() 的函数做一些事情。当 getThingy() 失败时会发生什么?来电者怎么知道?您在这里拥有的是一个例外(从概念上),您的设计应该反映这一点。

于 2012-08-27T17:44:55.833 回答
1

您可以使用运行时断言代替您的fatalError例程。这看起来像:

Thingy& getThingy(int id)
{
    for ( int i = 0; i < something(); ++i )
    {
        if ( thingyArray[i].id == id )
            return thingyArray[i];
    }
    // Clean up and error condition reporting go here.
    assert(false);
}
于 2012-08-27T17:47:45.637 回答