0

重複の可能性:
C でバイナリ ファイルを読み取るには? (動画、画像、テキスト)

C プログラムを使用してbmp ファイルの内容を読み込もうとしています。内容は読み取れますが、読み取った値が予想と矛盾しています。私のコードは次のとおりです。


FILE *fp=NULL;
fp=fopen("C:\\Users\\Saurabh\\Pictures\\nice.bmp","r");

if(fp!=NULL)
{
    printf("%c\n",fgetc(fp));
    printf("%c\n",fgetc(fp));

    printf("%c\n",fgetc(fp));
    printf("%c\n",fgetc(fp));
    printf("%c\n",fgetc(fp));
    printf("%c\n",fgetc(fp));
}

else
    printf("Error reading the file");

理解のために、ここではバイトごとに読んでいます。読み取っBMた最初の 2 バイトは正しいです。次の 4 バイトが読み取られます*t期待される値は 40 です。形式を参照してください。40誰かが何が起こっているのか、また変換を実行する必要がある場合にどのように値を取得できるのかを説明してください。

4

2 に答える 2

2

あなたの問題は、ファイルを開いた方法だと思います:

fp=fopen("C:\\Users\\Saurabh\\Pictures\\nice.bmp","r"); 

「r」はASCII読み取り用で、バイナリで開きたい:

fp=fopen("C:\\Users\\Saurabh\\Pictures\\nice.bmp","rb"); 

編集: fgetc() intを返すので、intを使用して戻り値を取得しようとしました。また、結果を16進数で表示したいので、16進数の出力形式を使用しましょう:

FILE *readf;
int i;
unsigned int size = 0;

//Open file
readf = fopen("blackbuck.bmp", "rb");

i = fgetc(readf);
printf("%#x\n",i);   // 0x42
i = fgetc(readf);
printf("%#x\n",i);   // 0x4D
for(i=0; i<3; i++)
    size |= fgetc(readf) << (i*8); // 0xC0036

この更新により、最初の 2 つの値が 0x42 0x4D になり、次の 3 バイトが連結されてビットマップのサイズが決まります (0xC0036 = 786486 バイト)。

この画像をテストに使用しました: http://people.sc.fsu.edu/~jburkardt/data/bmp/blackbuck.bmp

結果には、bmp ヘッダーの正しいバイト コードが含まれていることがわかります。0x42 0x4d the header field used to identify the BMP & DIB file is 0x42 0x4D in hexadecimal, same as BM in ASCII

于 2012-09-25T15:59:48.800 に答える
1

私はマイクに同意しますが、このファイルをバイナリモードで読み取る必要がありますが、まだ問題が発生しているわけではありません。最終的にはそうなりますが、サイズのいずれかのバイトに10または13が含まれていない限り、最初の6文字は壊れてはなりません。

intを読み取るために、次のようなことを行うことができます

int result;
fread(fp, sizeof (int), 1, &result);

ただし、これは移植性がないことに注意してください。(少なくとも32ビットintとネイティブバイトオーダーを想定しています。BMPは、その起源のため、リトルエンディアンです...そして、大きなサイズで一度にすべてを読み取ると、サイズはすべて奇抜になります-エンディアンマシン。)

別の方法:

unsigned long result = 0;
for (int i = 0; i < 4; ++i) {
     result |= (unsigned long) fgetc(fp) << (i * 8);
}

これは、少なくとも常に正しいバイト数を読み取り、エンディアンを考慮に入れる必要があります。またunsigned long、32ビットの数値を保持するのに十分な長さですが、int(符号なしでも)保持できるとは限りません。

于 2012-09-25T16:19:40.020 に答える