no matching constructor for initialization of 'string' (aka 'basic_string<char>')

浪尽此生 提交于 2021-02-16 20:31:18

问题


Here is the code:

#include <iostream>
#include <string>

using namespace std; 

class Foo { 
public:
    operator string() const { return n; }
    string n {"foo"};
};

int main (int argc, char** argv) {

    string s {Foo{}};
    cout << s << endl;

    return 0;
}

This code compiles using gcc 4.8.3, but it does not compile using clang 3.5, can someone tell me what's wrong with it?

I got an error like this:

main.cpp:45:12: error: no matching constructor for initialization of 'string' (aka 'basic_string<char>')
    string s {Foo{}};
           ^ ~~~~~~~

clang --version:

clang version 3.5.0 (tags/RELEASE_350/final 216961)
Target: x86_64-suse-linux
Thread model: posix

Thanks


回答1:


I believe this is a clang bug. According to the rules for list-initialization in [dcl.init.list]:

List-initialization of an object or reference of type T is defined as follows:

  • If T is a class type and the initializer list has a single element of type cv U, where U is T or a class derived from T, [...]
  • Otherwise, if T is a character array and [...]
  • Otherwise, if T is an aggregate, [...]
  • Otherwise, if the initializer list has no elements [...]
  • Otherwise, if T is a specialization of std::initializer_list<E>, [...]
  • Otherwise, if T is a class type, constructors are considered. The applicable constructors are enumerated and the best one is chosen through overload resolution (13.3, 13.3.1.7). If a narrowing conversion (see below) is required to convert any of the arguments, the program is ill-formed.
  • [...]

T is a class type, so we consider the basic_string constructors. #7 in that list (the copy constructor) is an applicable, viable constructor and so it should be chosen. At that point, these expressions should be equivalent:

struct Foo {
    operator std::string() const { return "hello"; }
};

std::string s{Foo{}};  // error
std::string s(Foo{});  // OK
std::string s = Foo{}; // OK

For some reason though, in the list-initialization case, clang complains that there is:

no known conversion from Foo to const std::__cxx11::basic_string<char> & for 1st argument

There is though, so I filed this as LLVM Bug 23658.



来源:https://stackoverflow.com/questions/30461583/no-matching-constructor-for-initialization-of-string-aka-basic-stringchar

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!