g ++ 4.6.3将文件内容读入字符串解析歧义

时间:2015-04-24 12:36:24

标签: c++ g++

我想阅读ifstream的内容

#include <vector>
#include <iterator>
#include <fstream>

std::ifstream stream;
std::vector<char> buf(std::istreambuf_iterator<char>(stream),
    std::istreambuf_iterator<char>());

但是当我说:

if(buf.size())
...

我收到错误

error: request for member 'size' in 'buf', which is of non-class type 'std::vector<char, std::istreambuf_iterator<char, std::char_traits<char> > >(std::istreambuf_iterator<char, std::char_traits<char> >, std::istreambuf_iterator<char, std::char_traits<char> > (*)())'

因此编译器认为我声明的是函数而不是vector<char>。我怎样才能使它发挥作用?

我使用-std=c++0x

编译g++-4.6.3

这个问题更多的是解析消歧而不是阅读文件。

1 个答案:

答案 0 :(得分:5)

这就是为什么人们应该使用花括号进行初始化:

std::vector<char> buf { 
                        std::istreambuf_iterator<char>(stream),
                        std::istreambuf_iterator<char>() 
                       };

在您的情况下,buf 一个对象 - 它是一个函数声明。在c ++中搜索 vexing parse 以了解它为什么是函数声明的解释。这里有相当多的主题。

好的。以下是您的代码所发生的情况。这段代码:

 std::vector<char> buf(std::istreambuf_iterator<char>(stream),
                      std::istreambuf_iterator<char>());
编译器将

视为函数声明,其中:

  • 函数名称为buf,返回std::vector<char>
  • 它需要两个类型的参数:
    • std::istreambuf_iterator<char>(stream),这只是另一种写作方式std::istreambuf_iterator<char> stream parens在这种情况下是多余的)。
    • std::istreambuf_iterator<char>()这是一种功能类型再次 parens 在这种情况下不是多余的) - 它会衰减到一个函数指针类型,指向一个函数:
      • 没有任何内容并返回std::istreambuf_iterator<char>

所以你的代码变成了这个:

std::vector<char>                         //return-type
buf                                       //function-name
(
  std::istreambuf_iterator<char> stream,  //1st (named) parameter
  std::istreambuf_iterator<char> (*)()    //2nd (unnamed) parameter
);

希望有所帮助。