2013-12-11 42 views
1

我想打开一个文件并将其放入一个字符串中。我的代码是:使用ifstream加载文件时出错

#include <iostream> 
#include <fstream> 
#include <string> 
using namespace std; 

int main() { 
    streampos size; 
    char * memblock; 

    ifstream file ("C:\\a\\test.snt", ios::in | ios::binary | ios::ate); 
    if (file.is_open()){ 

    size = file.tellg(); 
    memblock = new char [size]; 
    file.seekg (0, ios::beg); 
    file.read (memblock, size); 
    file.close(); 

    std::string someString(memblock); 

    if(file.bad()){cout << "Bad\n";} 
    if(file.fail()){cout << "Fail\n";} 

    delete[] memblock; 
    }else{ cout << "Unable to open file";} 

    return 0; 
} 

问题是,它不会加载大部分只有一小部分作为这样的“YYYY««««««««îþîþ”。 我想,当用记事本打开++文件看起来像这样Notepad++ http://gyazo.com/9d8dc182d5dfa06610372462831cca0e.png

回答

1
std::string someString(memblock); 

应该

std::string someString(memblock, size); 

构造的前一版本创建someString治疗memblock作为C风格的字符串,终止于第一个字节的值为0。这可能会导致创建太短的字符串;对于其他文件内容,您最终可能会超出您分配的内存。

后一版本使用memblock的全部内容创建someString,包括任何0字节。

1
std::string someString(memblock); 

这里,我们使用的字符串构造函数,一个const char*和读取,直到第一个空字节,因为它没有其他办法知道如何读取的字节数。

  • 在您的二进制文件中,其中一个空字节出现得相当早。
  • 如果你的文件没有空字节,字符串构造函数会继续读取甚至超出你分配的内存,造成危险和灾难。

相反,使用字符串构造能精确读取的字节数,你告诉它,无论什么样的字节值是:

std::string someString(memblock, size);