2013-03-20 80 views
0

我在Visual Studio C++中编写了一个简单的控制台应用程序。我想读012kb扩展到一个字节数组的二进制文件。尝试读取二进制文件时出现问题C++

ifstream inFile; 
size_t size = 0; 
char* oData = 0; 
inFile.open(path, ios::in|ios::binary); 

if (inFile.is_open()) 
{ 
    size = inFile.tellg();  // get the length of the file 
    oData = new char[size+1]; // for the '\0' 
    inFile.read(oData, size); 
    oData[size] = '\0' ;  // set '\0' 

    inFile.close(); 
    buff.CryptoContext = (byte*)oData; 
    delete[] oData; 
} 

但是,当我启动它,我在所有的oData字符接收到相同的字符,每次一个又一个,例如:

oData = "@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@...". 

然后我尝试另一种方式:

std::ifstream in(path, std::ios::in | std::ios::binary); 

if (in) 
{ 
    std::string contents; 

    in.seekg(0, std::ios::end); 
    contents.resize(in.tellg()); 

    in.seekg(0, std::ios::beg); 
    in.read(&contents[0], contents.size()); 

    in.close(); 
} 

现在内容有非常奇怪的值:一部分值是正确的,一部分是负值和奇怪值(可能与signed char和有关?)。

有没有人有任何想法?

谢谢!

+0

行'in.read(&contents [0],contents.size())'*可能*未定义的行为,*绝对*一个非常坏的主意。 – DevSolar 2013-03-20 12:04:39

回答

1

您正在将CryptoContext设置为指向byte指针的数据,然后删除该数据!

buff.CryptoContext = (byte*)oData; 
delete[] oData; 

此行后面CryptoContext指向已发布和无效的数据。只要将oData数组在存储器中保留更长时间,并在完成解码或您正在处理的任何内容后将其删除。

1

看一下第一个版本:

是什么让你认为tellg获取流的大小?它不,它returns the current read position。然后,您继续将指向您的数据的指针指向buff.CryptoContents,并及时删除指向的数据!这是非常危险的做法;您需要复制数据,使用智能指针或以其他方式确保数据具有正确的使用寿命。如果您在调试模式下运行,那么删除操作很可能会使用标记来标记您的数据以显示它已被删除,这就是为什么您要获取相同字符的流。

我怀疑你对第二个签名和未签名的建议可能是正确的,但我不能说没有看到你的文件和数据。