[英]C# BinaryWriter Write Method String Size
使用 C# 將字符串寫入二進制文件時,長度(以字節為單位)會自動添加到輸出中。 根據MSDN 文檔,這是一個無符號整數,但也是一個字節。 他們給出的示例是單個 UTF-8 字符將是三個寫入字節:1 個大小字節和 2 個字符字節。 這對於長度不超過 255 的字符串很好,並且與我觀察到的行為相匹配。
但是,如果您的字符串長於 255 個字節,則無符號整數的大小會根據需要增加。 作為一個簡單的例子,將 1024 個字符視為:
string header = "ABCDEFGHIJKLMNOP";
for (int ii = 0; ii < 63; ii++)
{
header += "ABCDEFGHIJKLMNOP";
}
fileObject.Write(header);
導致字符串前有 2 個字節。 創建一個 2^17 長度的字符串會導致一個有點令人抓狂的 3 字節數組。
因此,問題是如何知道讀取多少字節才能獲得讀取時的大小? 我不一定先驗地知道標題大小。 最終,我是否可以強制 Write(string) 方法始終使用一致的大小(比如 2 個字節)?
一種可能的解決方法是編寫我自己的 write(string) 方法,但出於明顯的原因,我想避免這種情況( 此處和此處的類似問題都接受此作為答案)。 另一個更可口的解決方法是讓讀者查找開始 ASCII 字符串信息的特定字符(可能是不可打印的字符?),但這並非萬無一失。 最后的解決方法(我能想到的)是強制字符串在特定大小字節數的大小范圍內; 再一次,這不是理想的。
雖然強制字節數組的大小保持一致是最簡單的,但我可以控制讀取器,因此也歡迎任何聰明的讀取器解決方案。
BinaryWriter
和BinaryReader
不是寫入二進制數據的唯一方法; 很簡單:它們提供了在特定讀者和作者之間共享的約定。 不,您不能告訴他們使用其他約定 - 除非您當然對它們進行子類化並完全覆蓋ReadString
和Write(string)
方法。
如果您想使用不同的約定,那么只需:不要使用BinaryReader
和BinaryWriter
。 使用您想要獲取字節和字節數的任何文本Encoding
直接與Stream
對話非常容易。 然后你可以使用任何你想要的約定。 如果您只需要寫入最多 65k 的字符串,那么請確保:使用固定的 2 個字節(無符號短整型)。 當然,您還需要決定哪個字節先出現(“字節序”)。
至於前綴的大小:它本質上是使用:
int byteCount = this._encoding.GetByteCount(value);
this.Write7BitEncodedInt(byteCount);
與:
protected void Write7BitEncodedInt(int value)
{
uint num = (uint) value;
while (num >= 0x80)
{
this.Write((byte) (num | 0x80));
num = num >> 7;
}
this.Write((byte) num);
}
這種類型的長度編碼非常常見 - 例如,它與“protobuf”使用的“varint”的想法相同(base-128,最低有效組在前,在 7 位組中保留位順序,第 8 位為續)
如果你想自己寫長度:
using (var bw = new BinaryWriter(fs))
{
bw.Write(length); // Use a byte, a short...
bw.Write(Encoding.Unicode.GetBytes("Your string"));
}
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.