靈感來自這個問題,我可以使用該iconv
命令產生帶有 BOM 和指定字節序的 UTF-16 輸出嗎?
該iconv
命令將文字從一種編碼轉換為另一種編碼。
例如:
echo hello | iconv -f ascii -t utf-16
生成 的 UTF-16 表示形式"hello\n"
。
UTF-16 檔案通常(但並非總是)以位元組順序標記 (BOM) 開頭,它是 Unicode 字元的 2 位元組編碼U+FEFF
。您可以透過檢查前兩個位元組是否為FE FF
或 來確定帶有 BOM 的 UTF-16 檔案的位元組序FF FE
。
此iconv
命令有多個用於產生 UTF-16 輸出的選項:
$ iconv --list | grep -i utf-16
UTF-16//
UTF-16BE//
UTF-16LE//
這個命令:
echo hello | iconv -f ascii -t utf-16be
生成大端 UTF-16無物料清單;它似乎假設如果您指定了位元組順序,則不需要在輸出中指出它。同樣,utf-16le
產生沒有 BOM 的小端 UTF-16。
這:
echo hello | iconv -f ascii -t utf-16
生成(在我的 x86 Ubuntu 系統上)little-endian UTF-16和BOM——但我見過一個類似的命令產生帶有 BOM 的大端 UTF-16 的報告,即使在小端系統上也是如此。
我始終可以使用utf-16be
或utf-16le
手動添加 BOM,但我正在尋找僅使用該iconv
命令的解決方案。
另一個解決方法,如果你知道字節序-t utf-16
會產生什麼,是:
echo hello | iconv -f ascii -t utf-16 | dd conv=swab 2>/dev/null
我會做什麼喜歡使用類似:
iconv -f ascii -t utf-16bebom # big-endian with BOM
iconv -f ascii -t utf-16lebom # little-endian with BOM
但iconv
不支持這一點。
編輯 :
有權存取 x86 Mac OSX 系統的人可以發表評論,顯示以下命令的(複製和貼上)輸出嗎?
echo hello | iconv -f ascii -t utf-16 | od -x
答案1
不,如果指定位元組順序,iconv
則不插入 BOM。
這是來自統一碼聯盟
Q:我該如何處理 BOM?
答:以下是一些需要遵循的準則:
- 特定協定(例如 Microsoft .txt 檔案約定)可能需要在某些 Unicode 資料流(例如檔案)上使用 BOM。當您需要遵守此類協議時,請使用 BOM。
- 某些協定允許在未標記文字的情況下使用可選的 BOM。在那些情況下,
- 如果已知文字資料流是純文本,但編碼未知,則可以使用 BOM 作為簽章。如果沒有 BOM,則編碼可以是任何內容。
- 如果已知文字資料流是純 Unicode 文字(但不知道哪種位元組序),則可以使用 BOM 作為簽章。如果沒有 BOM,則文本應解釋為 big-endian。
- 一些面向位元組的協定期望在檔案開頭使用 ASCII 字元。如果 UTF-8 與這些協定一起使用,則應避免使用 BOM 作為編碼形式簽署。
- 如果資料流的精確類型已知(例如 Unicode big-endian 或 Unicode Little-endian),則不應使用 BOM。尤其, 每當資料流聲明為 UTF-16BE、UTF-16LE、UTF-32BE 時 或 UTF-32LE BOM一定不使用。
(我的重點)
我希望iconv
嘗試忠於這些準則的最後一條。
更新。
題外話
在我看來:
指定 BOM 的選項無疑是 iconv 的一個有用的附加功能。
沒有 BOM 的 UTF-16LE 文件是可以在 Windows 中使用,儘管有時需要額外的努力。例如,記事本的檔案開啟對話框允許您選擇“Unicode”,這是微軟對“UTF-16LE”的名稱,並且(毫不奇怪)似乎適用於沒有 BOM 的檔案。
我可以按照通常的方式在 Windows 記事本 (XP) 中開啟 UTF-16LE 測試檔案(無 BOM)或 UTF-8 測試檔案(無 BOM),例如在資源管理器中雙擊檔案名稱。這對我來說似乎有用。我知道有時 Windows 會錯誤地猜測編碼 - 在這種情況下,您必須在開啟檔案時告訴記事本編碼。這種不便意味著包含 BOM 更適合在 Windows 上使用的文字檔案。
如果特定應用程式無法使用任何帶有 BOM 的 UTF-16LE 檔案以外的文件,那麼我同意不帶 BOM 的 UTF-16LE 檔案不可用於該特定應用程式。
我懷疑如果你可以讓一切都使用UTF-8(無BOM),從長遠來看這是最好的解決方案。
然而問題的答案“我可以使用 iconv 命令產生帶有 BOM 和指定字節序的 UTF-16 輸出嗎“ 目前 ”不」。
答案2
如果要將 BOM 加入到檔案中,可以手動新增:
對於 UTF-8 BOM(EF BB BF)
file='main.cpp'
printf '\xEF\xBB\xBF' > $file.utf8
iconv -f ASCII -t UTF-8 $file >> $file.utf8
mv -v $file.utf8 "converted-$file"
對於 UTF-16BE BOM(FE FF)
file='main.cpp'
printf '\xFE\xFF' > $file.utf16be
iconv -f ASCII -t UTF-16BE $file >> $file.utf16be
mv -v $file.utf16be "converted-$file"
對於 UTF-16LE BOM(FF FE)
file='main.cpp'
printf '\xFF\xFE' > $file.utf16le
iconv -f ASCII -t UTF-16LE $file >> $file.utf16le
mv -v $file.utf16le "converted-$file"
筆記:
您可能會注意到每種情況下的 BOM 都不同。你可以找到更多資訊請點擊此處: