C++ 如果函数值为null,则返回

C++ 如果函数值为null,则返回,c++,C++,我正在编写一个练习编译器,lookup_helper(key,current)返回一个指向某个符号的指针(如果在当前范围内找到该符号)。 for()循环在所有作用域中循环并搜索某个符号,直到找到并返回它。否则将返回null ptr Symbol * lookup() { //.... //.... //search all scopes for (int i = Scopes.size(); i > 0; i--)

我正在编写一个练习编译器,lookup_helper(key,current)返回一个指向某个符号的指针(如果在当前范围内找到该符号)。 for()循环在所有作用域中循环并搜索某个符号,直到找到并返回它。否则将返回null ptr

    Symbol * lookup()
    {

     //....
     //....

    //search all scopes
    for (int i = Scopes.size(); i > 0; i--)
            {
                Scope current = Scopes[i - 1];

                if (lookup_helper(key, current)) //not good design
                    return lookup_helper(key, current); //calling second time

            }
        return nullptr; //not found
    }

这段代码不是调用lookup\u helper()两次吗?一次在if()中,一次在return中?我有这个问题的解决方案,但我正在寻找一个更优雅的解决方案,只调用一次lookup\u helper(我也不想创建一些变量来存储返回值)。也许我所问的是不可能的,因为我必须跳转到代码的执行中,以确定lookup_helper是否返回nullptr

我想象的优雅:(不是这样工作的)


是的,您的代码调用
lookup\u helper
两次。如果某些编译器知道函数是“纯的”(使用GCC术语),那么它们可能能够消除第二个调用。但是,C++中的那些“优化”是手动和显式更好地完成的。 至于如何避免第二次调用,通常是在尝试分析结果之前将结果存储在中间变量中

...
Symbol *symbol = lookup_helper(key, current);
if (symbol != nullptr)
  return symbol;
....

如果局部变量位于最内部的范围内,则可以执行以下操作

for (int i = Scopes.size(); i > 0; i--) {
    if (auto ret = lookup_helper(key, Scopes[i])) {
        return ret;
    }
}
还是更传统的

for (int i = Scopes.size(); i > 0; i--) {
    auto ret = lookup_helper(key, Scopes[i]);
    if (ret) {
        return ret;
    }
}

是,您的代码将调用查找帮助程序两次。一个简单的解决方案是将结果存储到局部变量中:

...
for(auto & scope : Scopes) {
    auto ret = lookup_helper(key, scope);
    if(ret) return ret;
}
...

为什么不使用局部变量呢?在OP中,我说这不是我想做的事情。我正在寻找该语言的一个特性(比如lambda或其他东西),它允许它只调用一次函数。最后一个例子是哪种方式?仍然调用
lookup\u helper
两次,加上现在检查(尝试)两次?很抱歉,我输入了上一个示例,更新了OP~“我不想创建一些变量来存储返回值”——为什么不?避免这样做的理由是什么?if()语句返回什么?如果ret不为空,则为true?我喜欢that@user3465668
lookup\u helper
函数返回指针,因此
auto-ret
是指针类型。
操作符=
返回对修改对象(即指针)的引用。最后,
T*ptr=nullptr;if(ptr){…}
说明了上面的if(auto-ret=lookup\u helper(…)工作的原因。
...
for(auto & scope : Scopes) {
    auto ret = lookup_helper(key, scope);
    if(ret) return ret;
}
...