2011-12-17 56 views
10

我需要能夠劃定二進制數據流。我正在考慮使用ASCII EOT(End of Transmission)字符來做到這一點。劃分二進制序列

但是我有點擔心 - 我怎麼能確定用於這個(0b00000100)的特定二進制序列不會出現在我自己的二進制序列中,因此給出了定界誤報?

換句話說,如何最好地處理二進制分隔?

編輯:...沒有使用長度標題。對不起,你應該提到過這個。

回答

7

通常,您將二進制數據打包爲衆所周知的格式,例如使用描述後續數據的固定標頭。如果您試圖在未知數據流中查找分隔符,通常需要一個轉義序列。例如,像HDLC,其中0x7E是幀分隔符。必須對數據進行編碼,使得如果數據中有0x7E,則將其替換爲0x7D,後跟原始數據的XOR。數據流中的0x7D也同樣被轉義。

3

如果二進制記錄可以真正包含任何數據,請嘗試在數據之前添加一個長度,而不是數據之後的標記。這有時稱爲前綴長度,因爲長度在數據之前。

否則,您將不得不逃離字節流中的分隔符(並轉義轉義序列)。

3

您可以在其之前預先設置二進制數據的大小。如果您正在處理流式數據並且事先不知道其大小,則可以將其分成塊,並且每個塊都以大小字段開始。

如果你設置了一個塊的最大大小,你將會得到除最後一個塊以外的所有塊都相同的長度,如果你需要它將簡化隨機訪問。

10

你有五個選項:

  • 使用一個分隔符,這是不太可能發生。這可能會導致您猜錯的風險。我不推薦這種方法。
  • 使用分隔符和escape sequence來包含分隔符。您可能需要將轉義字符加倍,具體取決於使解析更簡單的原因。 (請考慮C \0在某些內容中包含ASCII NUL。)
  • 使用分隔符詞組您可以確定不會發生。 (想想mime message boundaries。)
  • 預先編制一個長度字段的某種類型,所以你知道讀取下面的N個字節作爲數據。這有一個缺點,就是在寫入數據之前要求你知道這個長度,這有時是困難的或不可能的。
  • 使用更復雜的東西,如ASN.1,完全描述全部您的內容。 (我不知道我是否真的推薦這個,除非你可以使用好的 - 在最好的情況下使用ASN.1是很尷尬的,但它確實允許完全明確的二進制數據解釋。)