utf-8에서 ms-ansi로 파일을 변환하려고 합니다.
나는 사용한다
iconv -f UTF8 -t MS-ANSI// < data.txt
하지만 얻을
iconv: illegal input sequence at position 171359
이를 조사할 때
dd if=data.txt of=error.txt bs=1 count=10 skip=171359
알겠어요:
hexdump -C error.txt
00000000 ef bb bf 38 3a 6e 61 09 38 3a |...8:na.8:|
0000000a
파일이 utf-8이 아닙니다. 그렇지 않은 경우 대신 iconv를 사용해야 합니까?
답변1
$ printf '\xef\xbb\xbf' | uconv -x any-name
\N{ZERO WIDTH NO-BREAK SPACE}
이는 바이트 순서 표시로도 사용되는 문자(U+FEFF, 3바이트 UTF-8로 인코딩됨)입니다. 어떤 경우에도 해당 문자는 MS-ANSI에서 찾을 수 없으므로(때때로 windows-1252(iso8859-1의 상위 집합)에서 잘못된 이름이 지정됨) 해당 문자로 변환할 수 없습니다.
BOM은 UTF16-LE와 UTF16-BE(또는 CPU 엔디안의 영향을 받는 기타 비바이트 인코딩)를 구별하기 위해 일부 텍스트의 시작 부분에 사용됩니다. 바이트 순서 모호성이 없는 UTF-8에서는 의미가 없으며 단일 바이트 문자 집합 windows-1252에서는 더욱 그렇습니다. "너비가 0인 공백"이므로 표시되지 않으며 "0-너비 공백" 문자처럼 단어를 구분하는 속성이 없으므로 완전히 제거하는 것이 안전할 수 있습니다.
zsh
, 또는 :bash
ksh93
sed $'s/\ufeff//g' < input | iconv -t windows-1252
일부 iconv
구현의 경우 다음을 사용할 수도 있습니다.
iconv -t windows-1252//translit < input
//translit
텍스트를 충실하게 번역할 수 없는 경우 근사치를 사용합니다. 이 경우 U+FEFF 문자만 제거됩니다.
$ printf '\xef\xbb\xbf\x38\x3a\x6e\x61\x09\x38\x3a' |
iconv -t windows-1252//translit | hd
00000000 38 3a 6e 61 09 38 3a |8:na.8:|
00000007
또 다른 옵션은 다음을 사용하는 것입니다.
iconv -t utf-16le | iconv -f utf-16 -t windows-1252
첫 번째는 iconv
BOM이 없는 UTF-16 리틀 엔디안으로 변환되지만 초기 U+FEFF는 BOM이 있는 실제 UTF-16으로 변환하므로 두 번째는 iconv
섹션 순서라는 단어의 인코딩을 결정하는 데 사용되므로 해당 BOM을 제거합니다 utf-16
.