2010-06-27 3 views
28

배치 파일로 사용할 스크립트가 있으면 (성공하지 않고) UTF-8 텍스트 파일에 BOM이 없으면 추가 할 수 있습니다.UTF-8 파일에 BOM 추가하기

필자가 쓰는 언어 (perl, python, c, bash) 나 운영체제는 나에게 중요한 문제가 아닙니다. 나는 다양한 컴퓨터에 접근 할 수있다.

BOM을 제거하는 많은 스크립트를 발견했습니다. 많은 Windows 프로그램이 UTF-8 텍스트 파일을 읽지 못하는 경우 바보처럼 들립니다. BOM.

분명히 놓치셨습니까? 감사합니다.

답변

4

매우 간단합니다. 파일을 가정하면 항상 UTF-8 (당신은 인코딩을 감지하지 못하고있어, 당신은에게 인코딩을 알고 )입니다 :

은 처음 세 문자를 읽어들입니다. 그것들을 UTF-8 BOM 시퀀스와 비교하십시오 (wikipedia는 0xEF, 0xBB, 0xBF라고 말합니다). 동일하면 새 파일로 인쇄 한 다음 원본 파일의 모든 항목을 새 파일로 복사하십시오. 다른 경우 먼저 BOM을 인쇄 한 다음 세 문자를 인쇄 한 다음 원래 파일의 모든 내용을 새 파일로 인쇄하십시오.

C에서 fopen/fclose/fread/fwrite이면 충분합니다.

39

나는이 addbom.sh를 'file'명령과 ICU의 'uconv'명령을 사용하여 작성했습니다.

#!/bin/sh 

if [ $# -eq 0 ] 
then 
     echo usage $0 files ... 
     exit 1 
fi 

for file in "[email protected]" 
do 
     echo "# Processing: $file" 1>&2 
     if [ ! -f "$file" ] 
     then 
       echo Not a file: "$file" 1>&2 
       exit 1 
     fi 
     TYPE=`file - < "$file" | cut -d: -f2` 
     if echo "$TYPE" | grep -q '(with BOM)' 
     then 
       echo "# $file already has BOM, skipping." 1>&2 
     else 
       (mv "${file}" "${file}"~ && uconv -f utf-8 -t utf-8 --add-signature < "${file}~" > "${file}") || (echo Error processing "$file" 1>&2 ; exit 1) 
     fi 
done 

편집 : mv 인수 주위 추가 따옴표. 감사합니다 @DirkR 그리고 다행이 스크립트가 도움이되었습니다!

+1

절대적으로 완벽! 내가 온 것보다 훨씬 낫다. 많은 감사. – Stephane

+2

"$ @"가 $ *보다 낫습니다. 인수로 공백을 유지합니다. (windows + cygwin에서 유용합니다.) – mcoolive

+0

@mcoolive thanks –

0

나는 나는 그런 사소한 일을 자신을 작성하지 않습니다 생각하지만 일부 문자 집합 변환을 할 필요가 있기 때문에, 여기은 : 원래의 파일 이름으로

#!/usr/bin/python 
import os 
import sys 
import codecs 

INPUT_ENCODING = codecs.BOM_UTF16_LE # 'utf_16_le' 
OUTPUT_ENCODING = 'utf-8-sig'   # is there a constant for this?? 

if len(sys.argv) == 1: 
    print 'Usage:\n\t%s <filename.txt>' % sys.argv[0] 
    sys.exit(-1) 

output_file = os.path.splitext(os.path.split(sys.argv[1])[-1])[0] 
fin = codecs.open(sys.argv[1], 'rb', encoding=INPUT_ENCODING) 
fout = codecs.open(output_file + '_utf8bom.txt', 'wb', encoding=OUTPUT_ENCODING) 
fout.write(fin.read()) 
fin.close() 
fout.close() 

print 'done' 

전화를 만 즉 :

# utf8bom_add.py myfilename.txt 

그리고 당신은 UTF-8UTF-8 변환하는 경우 그 정확한 값으로 INPUT_ENCODING을 변경합니다.

10

(yingted에 의해 https://stackoverflow.com/a/9815107/1260896에 따라 응답)

는 "foo-"로 시작하는 모든 파일에 BOM을 추가하려면, 당신은 sed를 사용할 수 있습니다. sed에는 백업을 할 수있는 옵션이 있습니다.당신이 확실히 알고 더 BOM이 이미 존재하지 않는 경우

sed -i '1s/^\(\xef\xbb\xbf\)\?/\xef\xbb\xbf/' foo-* 

, 명령 단순화 할 수 있는지 확인

sed -i '1s/^/\xef\xbb\xbf/' foo-* 

당신이 즉, UTF-16이 다르기 때문에, 그렇지 않으면 (UTF-8로 설정해야 확인 나는 그것을 알고

#!/usr/bin/env bash 

#Add BOM to the new file 
printf '\xEF\xBB\xBF' > with_bom.txt 

# Append the content of the source file to the new file 
cat source_file.txt >> with_bom.txt 

이다 나는이 찾을 How can I re-add a unicode byte order marker in linux?)

+1

UTF-8의 경우'\ xef \ xbb \ xbf'를 사용하십시오. UTF-16 리틀 엔디안 사용을위한 '\ xff \ xfe'; UTF-16 빅 엔디안 사용은'\ xfe \ xff'입니다. https://www.w3.org/International/questions/qa-byteorder-mark –

+0

Mac에서이 기능이 작동하지 않습니다. 명령 줄'sed -i '1s/^/\ xef \ xbb \ xbf /'temp.csv'는'sed : 1 : "temp.csv"를주었습니다 : 정의되지 않은 레이블 'emp.csv " –

+0

@PerLundberg 수 있습니다 문제를 해결하려고 시도해보십시오.'sed '1s/asdfasdfasdf //'blah.csv'을 시도하십시오. -i가 없으면 입력 파일을 변경하지 않고 콘솔에 결과를 출력하므로 매우 안전합니다. 그 줄은 줄 1을보고 문자열 asdfasdfasdf를 검색하고 아무것도 바꾸지 말고 그 줄을 지워야합니다. 그런 다음'^ adsfasdfasdf'를 만드십시오.'^'가 줄의 시작을 표시합니다. 어쩌면 그것이 어떤 이유로 문제를 일으키는 것일 수 있습니다. 아마도 당신은 sed 스위치를 사용하여 아마도'^'처럼 사용할 수있게 할 필요가 있습니다. – barlop

15

가장 쉬운 방법을 확인 외부 프로그램 (고양이)를 사용합니다 ...하지만 OSX에서 테스트 bash는

에서 쉽게 일을 할 것입니다하지만,뿐만 아니라 그 파일이 이미 BOM이없는 있다고 가정

참고 리눅스에서 작동해야 (!)