在不使用变量的情况下实例化ifstream对象

时间:2011-11-05 01:42:52

标签: c++ templates iostream

我似乎无法在不将其存储在变量中的情况下打开文件。我可以这样做:

ifstream blob("somefile");
string line;
blob >> line;

但是当我尝试这个时:

string line;
ifstream("somefile") >> line;

编译器(clang)给出了这个错误:

t.cpp:7:23: error: invalid operands to binary expression ('ifstream' (aka 'basic_ifstream<char>') and 'string' (aka 'basic_string<char>'))
    ifstream("thing") >> i;
    ~~~~~~~~~~~~~~~~~ ^  ~
In file included from t.cpp:1:
In file included from /usr/include/c++/4.6/iostream:39:
In file included from /usr/include/c++/4.6/ostream:39:
In file included from /usr/include/c++/4.6/ios:42:
In file included from /usr/include/c++/4.6/bits/ios_base.h:42:
In file included from /usr/include/c++/4.6/bits/locale_classes.h:41:
In file included from /usr/include/c++/4.6/string:53:
/usr/include/c++/4.6/bits/basic_string.h:2679:5: note: candidate function [with _CharT = char, _Traits = std::char_traits<char>, _Alloc = std::allocator<char>] not
      viable: no known conversion from 'ifstream' (aka 'basic_ifstream<char>') to 'basic_istream<char> &' for 1st argument
    operator>>(basic_istream<char>& __is, basic_string<char>& __str);
    ^
In file included from t.cpp:1:
In file included from /usr/include/c++/4.6/iostream:40:
/    usr/include/c++/4.6/istream:121:7: note: candidate function not viable: no known conversion from 'string' (aka 'basic_string<char>') to
      '__istream_type &(*)(__istream_type &)' for 1st argument
      operator>>(__istream_type& (*__pf)(__istream_type&))
      ^
/usr/include/c++/4.6/istream:125:7: note: candidate function not viable: no known conversion 

... a few more hundred pages of crap ...

1 error generated.

那么,两者之间的区别是什么?使用其他类,直接调用它可以正常工作。是否涉及一些模板魔法使其模糊不清?

1 个答案:

答案 0 :(得分:3)

您发布的代码在C ++ 03中无效(即,直到2011年9月才是C ++语言标准)。在C ++ 03中,operator>>只有一个重载可以在这里考虑[我删除了所有模板代码,因为它不相关]:

istream& operator>>(istream&, string&);

请注意,std::istream参数是非const引用,因此无法使用临时std::istream对象。在您的代码中,您尝试在那里使用临时对象。

在C ++ 11中(即当前的C ++语言标准),还有一个额外的重载,它通过右值引用获取std::istream个对象。这允许通过该参数传递临时值。

Visual C ++已经支持C ++ 11的这个功能,正如Benjamin Lindley在评论中指出的那样,如果你使用Visual C ++ 2010或更高版本,你的代码确实会编译。如果您使用 -std = c ++ 0x 标志,那么Clang 的构建可能支持此功能。