#include <iostream>
#include <string>
void fnc (const std::string&)
{
std::cout<<1;
}
void fnc (std::string&&)
{
std::cout<<2;
}
int main()
{
fnc ("abc");
}
所有编译器都选择std::string&&
版fnc
,这是合乎逻辑的,因为临时std::string
是为参考绑定创建的,但我无法找到,其中它是在C ++ 14 Standard中描述的。
我在那里找到了一个段落(3.2):
- 标准转换序列S1是比转换序列更好的转换序列 标准转换序列S2,如果
[...]
- S1和S2是参考绑定(8.5.3),两者都不是指 声明的非静态成员函数的隐式对象参数 没有ref-qualifier,S1将右值引用绑定到 rvalue 和S2绑定一个左值参考
但事实并非如此,因为S1将右值引用绑定到左值(&#34; abc&#34;,const char [4]的左值)。 我在哪里可以找到描述,通过该描述选择第二个过载?
P.S。我指的是C ++ 14 Standard而不是C ++ 11,因为我知道,C ++ 11中存在一些与rvalue引用绑定相关联的缺陷报告。
答案 0 :(得分:7)
首先,编译器为"abc"
执行隐式数组到指针转换,因此"abc"
的类型变为const char*
。第二个(你可能错过了),const char*
通过std::string
non-explicit constructor of std::string
(链接中的#5)转换为右值 const char*
。构造的std::string
rvalue是第二次重载的完美匹配,因此选择了第二次重载。
答案 1 :(得分:2)
但事实并非如此,因为S1将左值引用绑定到左值(&#34; abc&#34;,const char [4]的左值)。
请注意,"abc"
是const char[4]
,而不是std::string
。但是fnc()
都将std::string
作为参数,并且引用不能直接绑定到不同类型的对象。因此,首先"abc"
需要隐式转换为std::string
,这是一个临时的,即一个右值。然后正如标准所说,将选择右值参考过载。
答案 2 :(得分:1)
res = [(x,y) for x,y in a if (str(x) != 'nan' and str(y) != 'nan' and str(y) != 'FREE_FROM')]
无法直接传递到"abc"
的任何重载中。对于它们两者,必须将其转换为(rvalue)fnc()
。但是,标准中引用的规则明确选择std::string
而不是fnc(std::string&&)
。