Китайские символы вместо латыни, записанной в файл

Это - дескрипторы файлов, оставленные открытыми на устройстве (которого Вы изменяли размер).

lvm (8) говорит:

On invocation, lvm requires that only the standard file descriptors stdin, stdout
and stderr are available. If others are found, they get closed and messages
are issued warning about the leak.
3
23.05.2017, 15:39
1 ответ

Я ранее заметил, что, если Вы берете ASCII, закодировал текст (или, эквивалентно, UTF-8 закодировал текст ASCII), и декодируйте его как UTF-16, Вы часто получаете “китайские символы” (различные в зависимости от того, декодируете ли Вы его как UTF-16BE или UTF-16LE). На основе этого я думаю, что Вы имеете дело со смешанной кодировкой. Мое предположение - это Commision.txt кодируется или как UTF-16BE или как UTF-16LE, это question.txt простой ASCII (или UTF-8 закодировал ASCII), и что Ваш newFile заканчивается как недопустимая комбинация кодировки из обоих файлов.

Вещи должны работать лучше при использовании того же кодирования в обоих файлах; вероятно, UTF-8 будет работать лучше всего. Если Вам нужен окончательный результат, чтобы быть в некотором другом кодировании, то можно использовать iconv для преобразования его (iconv -f UTF-8 -t UTF-16BE <newFile >newfile.utf16be.txt).


Эффективно, кодировка UTF-16 символов ASCII совпадает с кодированием ASCII, но с дополнительными символами NUL, вставленными между каждым символом ASCII наряду с еще одним NUL прежде или после всех (в зависимости от порядка байтов кодировки UTF-16). Это означает, что текст ASCII, закодированный или как UTF-8 или как UTF-16, будет выглядеть “нормальным”, когда непосредственно просматривается на терминале UTF-8 (т.е. Ваша “печать к консоли”).

Пока содержание файла разделено, любая среда просмотра обнаружения кодирования (например, редактор), вероятно, правильно обнаружит кодирование (или по крайней мере выберет то, которое является достаточно близким рассмотрением, что UTF-8 и много однобайтовых кодировок идентичны в диапазоне ASCII).

Но, у Вас есть sed смешивание файлов. К сожалению, sed не достаточно “умен”, чтобы понять, что он имеет дело с файлами с помощью двух различных текстовых кодировок. Вы заканчиваете с (согласно моему предположению) файл, который является главным образом закодированным UTF-16 (от Commision.txt) с UTF-8 закодированный раздел (от question.txt) в середине (или везде, где Ваш Q помещает его). Результат, вероятно, недопустим, если полностью декодируется как UTF-8, но возможно допустимый, когда полностью декодируется как UTF-16 (хотя с некоторым неожиданным содержанием, где данные UTF-8).


Вот пример:

Commision.txt UTF-16BE, закодированный ASCII (с BOM).

% xxd Commision.txt 
0000000: feff 0046 0069 0072 0073 0074 0020 006c  ...F.i.r.s.t. .l
0000010: 0069 006e 0065 000a 004c 0069 006e 0065  .i.n.e...L.i.n.e
0000020: 0020 0077 0069 0074 0068 0020 0061 0020  . .w.i.t.h. .a. 
0000030: 0075 0063 0020 0027 0071 0027 003a 0020  .u.c. .'.q.'.:. 
0000040: 0028 0051 0029 000a 004c 0061 0073 0074  .(.Q.)...L.a.s.t
0000050: 0020 006c 0069 006e 0065 000a            . .l.i.n.e..

question.txt ASCII (или UTF-8 закодировал ASCII).

% xxd question.txt
0000000: 5768 6174 2069 7320 7468 6520 6169 722d  What is the air-
0000010: 7370 6565 6420 7665 6c6f 6369 7479 206f  speed velocity o
0000020: 6620 616e 2075 6e6c 6164 656e 2073 7761  f an unladen swa
0000030: 6c6c 6f77 3f0a                           llow?.

Я комбинирую их с sed.

% sed '/Q/{
s/Q//g
r question.txt
}' Commision.txt >newFile

newFile путаница.

sed, удаленный Q как единственный байт (51) вместо его двухбайтового представления UTF-16 (00 51).
Это разрушает двухбайтовое выравнивание остальной части файла, дает общую длину, которая нечетна вместо даже и представляет ПУСТОЙ УКАЗАТЕЛЬ UTF-16 (0000).

% xxd newFile
0000000: feff 0046 0069 0072 0073 0074 0020 006c  ...F.i.r.s.t. .l
0000010: 0069 006e 0065 000a 004c 0069 006e 0065  .i.n.e...L.i.n.e
0000020: 0020 0077 0069 0074 0068 0020 0061 0020  . .w.i.t.h. .a. 
0000030: 0075 0063 0020 0027 0071 0027 003a 0020  .u.c. .'.q.'.:. 
0000040: 0028 0000 2900 0a57 6861 7420 6973 2074  .(..)..What is t
0000050: 6865 2061 6972 2d73 7065 6564 2076 656c  he air-speed vel
0000060: 6f63 6974 7920 6f66 2061 6e20 756e 6c61  ocity of an unla
0000070: 6465 6e20 7377 616c 6c6f 773f 0a00 4c00  den swallow?..L.
0000080: 6100 7300 7400 2000 6c00 6900 6e00 6500  a.s.t. .l.i.n.e.
0000090: 0a                                       .

Несмотря на путаницу, это выглядит хорошо в моем терминале UTF-8.

% cat newFile
First line
Line with a uc 'q': ()
What is the air-speed velocity of an unladen swallow?
Last line

Когда я загружаю его в Vim, однако вещи, очевидно, неправильно (после открывающей скобки существует на самом деле NUL, но ее присутствие вызвало это сообщение быть усеченным). Vim предупреждает “ОШИБКУ ПРЕОБРАЗОВАНИЯ в строке 2”.

First line
Line with a uc 'q': (⤀੗桡琠楳⁴桥⁡楲⵳灥敤⁶敬潣楴礠潦⁡渠畮污摥渠獷慬汯眿਀䰀愀猀琀 氀椀渀攀

Если я удаляю вопросительный знак из question.txt (чтобы дать четное число байтов снова) и повторно создать newFile, затем я возвращаю последнюю строку (хотя она застревает в конец второй строки), и избегайте предупреждения преобразования от Vim.

First line
Line with a uc 'q': (⤀੗桡琠楳⁴桥⁡楲⵳灥敤⁶敬潣楴礠潦⁡渠畮污摥渠獷慬汯眊Last line
5
27.01.2020, 21:17

Теги

Похожие вопросы