提问人:thor 提问时间:7/7/2014 最后编辑:Communitythor 更新时间:7/7/2014 访问量:38969
std::vector:无法将 'std::ostream {aka std::basic_ostream<char>}' lvalue 绑定到 'std::basic_ostream<char>&&'
std::vector : cannot bind 'std::ostream {aka std::basic_ostream<char>}' lvalue to 'std::basic_ostream<char>&&'
问:
我在尝试做一些简单的事情时遇到了一个令人困惑的错误消息,比如
std::cout << std::vector<int>{1,2,3};
其中说
cannot bind 'std::ostream {aka std::basic_ostream<char>}' lvalue to 'std::basic_ostream<char>&&'
int main() { std::cout << std::vector<int>{1,2,3}; }
(使用 gcc-4.8.1 和 -std=c++11 进行测试)
SO 也有类似的问题,例如重载运算符<<:无法将左值绑定到“std::basic_ostream<char>&&”,这是关于一些带有嵌套类的用户定义类。还有一个方法可以解决该问题的公认答案。
但我不知道这是否适用于.有人可以解释为什么这个错误会发生,以及如何解释它吗?std::vector
std::vector
谢谢
答:
与模板相关的错误消息有时会令人困惑。问题在于标准库没有定义用于插入(或任何其他容器,就此而言)到 .因此,编译器无法找到合适的重载,并尽可能地报告此故障(不幸的是,在您的情况下,这不太好/可读)。operator <<
std::vector
std::ostream
operator <<
如果要流式传输整个容器,可以使用 std::ostream_iterator
:
auto v = std::vector<int>{1, 2, 3};
std::copy(begin(v), end(v), std::ostream_iterator<int>(std::cout, " "));
至于为什么你会得到这个神秘的错误,分析完整的错误消息会有所帮助:
prog.cpp: In function ‘int main()’:
prog.cpp:13:37: error: cannot bind ‘std::ostream {aka std::basic_ostream<char>}’ lvalue to ‘std::basic_ostream<char>&&’
std::cout << std::vector<int>{1,2,3};
^
In file included from /usr/include/c++/4.8/iostream:39:0,
from prog.cpp:3:
/usr/include/c++/4.8/ostream:602:5: error: initializing argument 1 of ‘std::basic_ostream<_CharT, _Traits>& std::operator<<(std::basic_ostream<_CharT, _Traits>&&, const _Tp&) [with _CharT = char; _Traits = std::char_traits<char>; _Tp = std::vector<int>]’
operator<<(basic_ostream<_CharT, _Traits>&& __os, const _Tp& __x)
^
显然有一个模板重载,它采用类型的 lhs 参数和模板化的 rhs 参数;它的存在是为了允许插入到临时流中。由于它是一个模板,因此它将成为代码中表达式的最佳匹配项。但是,是一个左值,因此它不能绑定到 。因此错误。operator<<
std::ostream&&
std::cout
std::ostream&&
评论
std::ofstream("output.txt") << "Hi there\n";
类中没有为 类 定义。operator <<
std::vector
std::basic_ostream
你想要的是以下内容
for ( int x : std::vector<int> { 1, 2, 3 } ) std::cout << x << ' ';
std::cout << std::endl;
虽然它可以写得更简单
for ( int x : { 1, 2, 3 } ) std::cout << x << ' ';
std::cout << std::endl;
这是 gcc 的一个已知问题,我就此提交了增强请求。
“唯一”的问题是您尝试打印到控制台的内容没有.不幸的是,错误消息不是很有帮助。:(operator<<
顺便说一句,这个问题与 l 值和 r 值引用无关。一个最小的例子:vector
#include <iostream>
struct A { };
int main() {
A a;
std::cout << a;
}
有关血腥的细节,请参阅增强请求中的讨论。简而言之,gcc 开发人员已经尝试改进错误消息,但事实证明这是出了名的困难。
就其价值而言,在我看来,clang 带有 libc++ 的错误消息更清晰:
clang++ -std=c++11 -stdlib=libc++ -lc++abi main.cpp && ./a.out
main.cpp:7:15: error: invalid operands to binary expression ('ostream' (aka 'basic_ostream<char>') and 'A')
std::cout << a;
~~~~~~~~~ ^ ~
在这里,第一行清楚地说明了问题所在。
评论