[英]Not able to read whole file
我正在制作一个C ++程序,以便能够打开.bmp图像,然后将其放入2D数组中。 现在我有这样的代码:
#include <iostream>
#include <fstream>
#include <sstream>
#include <string>
#include "Image.h"
using namespace std;
struct colour{
int red;
int green;
int blue;
};
Image::Image(string location){
fstream stream;
string tempStr;
stringstream strstr;
stream.open(location);
string completeStr;
while(!stream.eof()){
getline(stream, tempStr);
completeStr.append(tempStr);
}
cout << endl << completeStr;
Image::length = completeStr[0x13]*256 + completeStr[0x12];
Image::width = completeStr[0x17]*256 + completeStr[0x16];
cout << Image::length;
cout << Image::width;
cout << completeStr.length();
int hexInt;
int x = 0x36;
while(x < completeStr.length()){
strstr << noskipws << completeStr[x];
cout << x << ": ";
hexInt = strstr.get();
cout << hex << hexInt << " ";
if((x + 1)%3 == 0){
cout << endl;
}
x++;
}
}
现在,如果我在256x256的测试文件上运行此程序,它将正常打印,直到达到0x36E并给出错误/不再继续为止。 发生这种情况是因为completeStr字符串无法接收bmp文件中的所有数据。 为什么无法读取bmp文件中的所有行?
您的代码有很多问题。 主要的原因(可能是造成问题的原因)是您以文本模式打开文件。 从技术上讲,这意味着如果文件中除了可打印字符和一些特定的控制字符(例如'\\ t')之外,都包含未定义的行为。 实际上,在Windows下,这意味着将0x0D,0x0A的序列转换为单个'\\n'
,并将0x1A解释为文件的末尾。 当读取二进制数据时,并不是真正想要的。 您应该以二进制模式( std::ios_base::binary
)打开流。
这不是一个严重的错误,但是如果您只打算读取文件,则不应真正使用fstream
。 实际上,很少使用fstream
:您应该使用ifstream
或ofstream
。 stringstream
同样适用(但读取二进制文件时,我看不到stringstream
任何作用)。
另外(这是一个真正的错误),您使用的是getline
的结果,而不检查是否成功。 阅读行的惯用法是:
while ( std::getline( source, ling ) ) ...
但像stringstream
,你不想使用getline
的二进制流; 它将删除所有的'\\n'
(已从CRLF映射)。
如果要将所有数据都存储在内存中,最简单的解决方案是:
std::ifstream source( location.c_str(), std::ios_base::binary );
if ( !source.is_open() ) {
// error handling...
}
std::vector<char> image( (std::istreambuf_iterator<char>( source ) ),
(std::istreambuf_iterator<char>()) );
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.