我認爲這是一個endian問題。即您將字節42
和4D
寫入您的short
值。但是你的系統是小端(我可能有錯誤的名字),它實際上從左到右讀取字節(在一個多字節整數類型中)而不是從右到左。
此代碼所演示:
#include <stdio.h>
int main()
{
union {
short sval;
unsigned char bval[2];
} udata;
udata.sval = 1;
printf("DEC[%5hu] HEX[%04hx] BYTES[%02hhx][%02hhx]\n"
, udata.sval, udata.sval, udata.bval[0], udata.bval[1]);
udata.sval = 0x424d;
printf("DEC[%5hu] HEX[%04hx] BYTES[%02hhx][%02hhx]\n"
, udata.sval, udata.sval, udata.bval[0], udata.bval[1]);
udata.sval = 0x4d42;
printf("DEC[%5hu] HEX[%04hx] BYTES[%02hhx][%02hhx]\n"
, udata.sval, udata.sval, udata.bval[0], udata.bval[1]);
return 0;
}
提供了以下輸出
DEC[ 1] HEX[0001] BYTES[01][00]
DEC[16973] HEX[424d] BYTES[4d][42]
DEC[19778] HEX[4d42] BYTES[42][4d]
所以,如果你想成爲便攜式你需要檢測你的系統的字節序,然後做一個如果需要,則進行字節混洗。圍繞交換字節的互聯網將會有很多例子。
後續問題:
我只問,因爲我的文件大小爲3,而不是196662
這是由於內存對齊的問題。 196662是字節36 00 03 00
,3是字節03 00 00 00
。大多數系統需要類型如int
等不能拆分多個內存words
。所以直覺你認爲你的結構是奠定了即時記憶像:
Offset
short magic_number; 00 - 01
int file_size; 02 - 05
short reserved_bytes[2]; 06 - 09
int data_offset; 0A - 0D
但32位的系統,這意味着files_size
在同一word
2個字節爲magic_number
,並在接下來的word
兩個字節上。大多數編譯器不會容忍這一點,所以在內存中的結構佈局方式實際上是這樣的:
short magic_number; 00 - 01
<<unused padding>> 02 - 03
int file_size; 04 - 07
short reserved_bytes[2]; 08 - 0B
int data_offset; 0C - 0F
所以,當你在36 00
讀你的字節流進入這讓你FILE_SIZE作爲填補區域得到03 00 00 00
。現在,如果您使用fwrite
來創建這個數據,它應該是正常的,因爲填充字節將被寫出。但是如果你的輸入總是按照你指定的格式,那麼用fread讀取整個結構是不合適的。相反,您需要分別閱讀每個元素。
...麪包亂用你的叮咬順序?你嘗試啃食嗎? – Mehrdad 2011-12-19 03:55:18
你的標題不是'fread'而不是'bread'嗎? – buruzaemon 2011-12-19 03:55:39
對不起。我仍然需要正確使用Lions Auto。我修好了 – 2011-12-19 04:00:05