Это разница между UTF-16LE
и UTF-16
UTF-16LE
с прямым порядком байтов без спецификация UTF-16
большаяили little endian с спецификацией
Таким образом, когда вы используете UTF-16LE
, спецификация является лишь частью текста.Вместо этого используйте UTF-16
, чтобы спецификация автоматически удалялась.Причина существования UTF-16LE
и UTF-16BE
заключается в том, что люди могут носить с собой «правильно закодированный» текст без спецификаций, что к вам не относится.
Обратите внимание, что происходит, когда вы кодируете с использованием одного кодирования и декодируете сдругой.(UTF-16
автоматически обнаруживает UTF-16LE
иногда, не всегда.)
>>> u'Hello, world'.encode('UTF-16LE')
'H\x00e\x00l\x00l\x00o\x00,\x00 \x00w\x00o\x00r\x00l\x00d\x00'
>>> u'Hello, world'.encode('UTF-16')
'\xff\xfeH\x00e\x00l\x00l\x00o\x00,\x00 \x00w\x00o\x00r\x00l\x00d\x00'
^^^^^^^^ (BOM)
>>> u'Hello, world'.encode('UTF-16LE').decode('UTF-16')
u'Hello, world'
>>> u'Hello, world'.encode('UTF-16').decode('UTF-16LE')
u'\ufeffHello, world'
^^^^ (BOM)
Или вы можете сделать это в оболочке:
for x in * ; do iconv -f UTF-16 -t UTF-8 <"$x" | dos2unix >"$x.tmp" && mv "$x.tmp" "$x"; done