c++ - 为什么{}作为函数参数不会导致歧义?

标签 c++ language-lawyer overload-resolution

考虑以下代码:

#include <vector>
#include <iostream>

enum class A
{
  X, Y
};

struct Test
{
  Test(const std::vector<double>&, const std::vector<int>& = {}, A = A::X)
  { std::cout << "vector overload" << std::endl; }

  Test(const std::vector<double>&, int, A = A::X)
  { std::cout << "int overload" << std::endl; }
};

int main()
{
  std::vector<double> v;
  Test t1(v);
  Test t2(v, {}, A::X);
}

https://godbolt.org/z/Gc_w8i

打印:
vector overload
int overload

为什么由于模棱两可的重载解析而不会产生编译错误?如果第二个构造函数被删除,我们将得到vector overload两次。 int如何/按哪种度量标准比{}更好地匹配std::vector<int>

可以肯定地进一步减少构造函数的签名,但是我只是被等效的代码所欺骗,并希望确保对该问题没有任何重要的认识。

最佳答案

[over.ics.list] 中,重点是我的

6 Otherwise, if the parameter is a non-aggregate class X and overload resolution per [over.match.list] chooses a single best constructor C of X to perform the initialization of an object of type X from the argument initializer list:

  • If C is not an initializer-list constructor and the initializer list has a single element of type cv U, where U is X or a class derived from X, the implicit conversion sequence has Exact Match rank if U is X, or Conversion rank if U is derived from X.

  • Otherwise, the implicit conversion sequence is a user-defined conversion sequence with the second standard conversion sequence an identity conversion.

9 Otherwise, if the parameter type is not a class:

  • [...]

  • if the initializer list has no elements, the implicit conversion sequence is the identity conversion. [ Example:

    void f(int);
    f( { } ); // OK: identity conversion
    

    end example ]


std::vector由构造函数初始化,粗体的项目符号将其视为用户定义的收敛。同时,对于int,这是身份转换,因此它胜过第一个c'tor的等级。

关于c++ - 为什么{}作为函数参数不会导致歧义?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/60509693/

相关文章:

c++ - 这些转换中的哪些应该是不明确的?

c++ - 用sort()对成员 vector 进行排序的比较函数

c++ - 在不知道模板参数的映射中获取派生类的模板参数类型

c++ - 为什么在返回未初始化的变量时编译器不报错?

c++ - 使用点后模板函数的特化会破坏编译

C++ 重载解析查询

c++ - 使用委托(delegate)构造函数来避免泄漏

css - 在CSS Flexbox中,为什么没有“justify-items”和“justify-self”属性?

c++ - 函数参数的破坏顺序是什么?

c++ - 混淆在右值和左值上重载成员函数