c++ 对于一个可选的函数参数,如果没有提供值,我可以使用什么机制来获得一个赋值?

56lgkhnf  于 2022-12-05  发布在  其他
关注(0)|答案(4)|浏览(104)

在Python中,我可以做如下操作:

def add_postfix(name: str, postfix: str = None):
  if base is None:
    postfix = some_computation_based_on_name(name)
  return name + postfix

所以我有一个可选参数,如果没有提供,它会被赋值。注意,我没有postfix的常量默认值。它需要计算。(这就是为什么我不能只有一个默认值)。
在C++中,我到达std::optional并尝试:

std::string add_postfix(const std::string& name, std::optional<const std::string&> postfix) {
  if (!postfix.has_value()) { postfix.emplace("2") };
  return name + postfix;
}

我现在意识到这是行不通的,因为std::optional<T&>在C++中不是一个东西。
但现在我应该使用什么机制来实现以下目标:

  • 保持const T的优势&:不得复印,不得修改原件。
  • 不必再做其他的postfix_,这样我就有了可选的和最后的。
  • 不用超负荷。
  • 在一个函数签名中包含多个这些可选参数。
9avjhtql

9avjhtql1#

您可以使用两个函数来执行此操作:

std::string add_postfix(const std::string& name, const std::string& postfix) {
// whatever
}

std::string add_default_postfix(const std::string& name) {
return add_postfix(name, "2");
}

或者,如果你喜欢重载,你可以把第二个写为重载,命名为add_postfix

cyej8jka

cyej8jka2#

一种可能性是使用std::string const*(指向const std::string的非常量指针)作为函数参数。

std::string add_postfix(const std::string& name, std::string const* postfix = nullptr) 
{
  std::string derivedSuffix;
  if(!postfix) 
  { 
    derivedSuffix = some_computation(name); 
    postfix = &derivedSuffix;
  }
  return name + *postfix;
}

derivedSuffix需要是一个对象,其持续时间至少与指针postfix指向它的时间一样长。因此,它不能完全包含在if(!postfix)块中,因为如果它是这样的话,那么在它之外使用*postfix将是无效的。从技术上讲,即使postfix不是nullptr,我们也会创建一个空的std::string,但我们永远不必复制一个包含实际值的std::string

afdcj2ne

afdcj2ne3#

根据您的使用情况,value_or似乎可以完成以下任务:

std::string add_postfix(const std::string& name,
                        const std::optional<std::string>& postfix)
{
    return name + postfix.value_or("2");
}

如果你真的想要optional<T&>optional<reference_wrapper<T>>可能就能胜任。

std::string add_postfix(const std::string& name,
                        const std::optional<std::reference_wrapper<const std::string>>& postfix)
{
#if 1
    const std::string postfix_ = "2";
    return name + postfix.value_or(postfix_).get();
#else    // or
    return name + (postfix.has_value() ? postfix->get() : "2");
#endif
}

Demo

kuuvgm7e

kuuvgm7e4#

您可以简单地写入:

std::string add_postfix(const std::string& name, const std::string& postfix = "default value")
{
   return name + postfix;
}

相关问题