C++ 调用函数中的歧义。隐式转换? #包括 void f(std::string&&rref){ } void f(std::string s){ } int main(){ std::string s=“s”; f(标准:移动);; }

C++ 调用函数中的歧义。隐式转换? #包括 void f(std::string&&rref){ } void f(std::string s){ } int main(){ std::string s=“s”; f(标准:移动);; },c++,c++11,move-semantics,overload-resolution,C++,C++11,Move Semantics,Overload Resolution,这段代码引起了歧义,我不知道为什么,可能是我对右值引用进行了显式转换 我的想法是,右值引用可以隐式地转换为左值。 但我不确定。请解释。std::string可以从类型为std::string的右值初始化。所以第二个函数是候选函数 使用value和rvalue引用重载是不可行的。更正常的设置是右值引用和左值引用重载: #include <string> void f(std::string&& rref){ } void f(std::string s){ }

这段代码引起了歧义,我不知道为什么,可能是我对右值引用进行了显式转换

我的想法是,右值引用可以隐式地转换为左值。
但我不确定。请解释。

std::string
可以从类型为
std::string
的右值初始化。所以第二个函数是候选函数

使用value和rvalue引用重载是不可行的。更正常的设置是右值引用和左值引用重载:

#include <string>

void f(std::string&& rref){
}

void f(std::string s){ 
}

int main() {
    std::string s = "s";
    f(std::move(s));
}

这将涵盖所有用例。

模糊性是什么?有编译器错误消息吗?为什么这里需要两个单独的重载?我不需要。我问是因为我好奇;)@J.Doe从技术上讲,表达式的类型
std::move
是值类别为xvalue的
std::string
。我没有比cppreference或stackoverflows更好的建议,因为这意味着std::move返回的std::string&&可以转换(通过转换构造函数)std::string(std::string&&other)to string?@J.Doe是的-
s
是使用该构造函数从参数初始化的。在更改的代码中,表达式
s
具有值类别左值,因此
f(std::string&)
不是候选项。
f(std::string)
被称为.@J.Doe,它们都需要在stackoverflow上匹配查找“what is xvalues”
void f(std::string&& rref);
void f(std::string & lref);   // or const&