当你对检索到的值的表达式进行分支时,是否存在像`if(Value*value = getValue())`这样的习惯用法?

Til*_*gel 13 c++ qstring qt

我经常使用普通的

if (Value * value = getValue())
{
    // do something with value
}
else
{
    // handle lack of value
}
Run Code Online (Sandbox Code Playgroud)

现在,我也经常这样做

QString error = someFunctionReturningAnErrorString(arg);
if (!error.isEmpty())
{
     // handle the error
}
// empty error means: no error
Run Code Online (Sandbox Code Playgroud)

这一切都很好,但我希望error变量的范围是if-block.那有一个很好的习语吗?显然,我可以将整个部分包装在另一个块中.

显然,这不起作用:

if(QString error = someFunctionReturningAnErrorString(arg), !error.isEmpty())
{
    // handle the error
}
// empty error means: no error
Run Code Online (Sandbox Code Playgroud)

不幸的是(但有充分的理由)QString无法转换为bool,所以这也不起作用:

if(QString error = someFunctionReturningAnErrorString(arg))
{
    // handle the error
}
// empty error means: no error
Run Code Online (Sandbox Code Playgroud)

有什么建议?

Lig*_*ica 10

没有.这样没有成语,没有这样的语法!

此外,您已经达到了不再值得使代码越来越混淆的程度.

只需像现在一样写它.

如果您真的不希望范围泄漏,请引入新范围:

{
   const QString error = someFunctionReturningAnErrorString(arg);
   if (!error.isEmpty()) {
      // handle the error
   }
}
// The above-declared `error` doesn't exist down here
Run Code Online (Sandbox Code Playgroud)

我使用这种模式已经相当多了,尽管我已经被指责成瘾,所以请按照你的意愿行事.


Bar*_*rry 6

在保持代码可理解的情况下使用该习惯用法的唯一方法是,如果您的函数返回一个可转换为bool的对象,其方式true表明您想要获取分支并且false意味着您不关心它.其他任何东西都只会导致只写代码.

可能相关的一个这样的对象恰好是boost::optional.鉴于:

boost::optional<QString> someFunctionReturningAnErrorString(T arg);
Run Code Online (Sandbox Code Playgroud)

你可以用自然的方式使用你想要的习语:

if (auto error = someFunctionReturningAnErrorString(arg)) {
    // ...
}
Run Code Online (Sandbox Code Playgroud)

这也有额外的好处,我认为optional错误消息在语义上比检查空错误消息更有意义.

  • "我认为`可选`错误消息比检查空错误消息更具语义意义." +1 (3认同)