
소스 파일의 각 행 시작 부분에 특수 문자가 있습니다. 파일은 이중 공백으로 구분됩니다.
샘플 데이터 파일:
âNAME ABC
âAGE 21
âADDRESS XYZ street ABC city
âCONTACT 13244235
âDOJ 20181212
â
각 줄의 첫 번째 특수 문자를 제거하고 파일을 ;
(세미콜론) 구분 파일 로 변환하고 싶습니다 .
아래 코드는 UAT에서는 잘 작동하지만 PROD에서는 제대로 작동하지 않는 코드입니다.
awk '{ print substr($0,1) }' FILE1.txt | sed 's/ /;/' > FILE2.txt
UAT 출력(예상되는 바람직한 출력):
NAME;ABC
AGE;21
ADDRESS;XYZ street ABC city
CONTACT;13244235
DOJ;20181212
PROD 출력:
âNAME;ABC
âAGE;21
âADDRESS;XYZ street ABC city
âCONTACT;13244235
âDOJ;20181212
동일한 코드가 UAT에서 제대로 작동합니다. 즉, 첫 번째 문자를 제거하고 파일을 ;
세미콜론으로 구분하여 변환하지만 PROD에서는 첫 번째 특수 문자를 제거하지 않고 파일을 세미콜론으로 구분하여 변환합니다.
출력 locale
:
locale
LANG=en_US.UTF-8
LC_CTYPE="en_US.UTF-8"
LC_NUMERIC="en_US.UTF-8"
LC_TIME="en_US.UTF-8"
LC_COLLATE="en_US.UTF-8"
LC_MONETARY="en_US.UTF-8"
LC_MESSAGES="en_US.UTF-8"
LC_PAPER="en_US.UTF-8"
LC_NAME="en_US.UTF-8"
LC_ADDRESS="en_US.UTF-8"
LC_TELEPHONE="en_US.UTF-8"
LC_MEASUREMENT="en_US.UTF-8"
LC_IDENTIFICATION="en_US.UTF-8"
LC_ALL=
누구든지 이것에 대해 나를 도울 수 있습니까 ..?
답변1
FILE1.txt
문제는 문자 인코딩에 대한 링크일 수 있다고 생각합니다. 두 환경 모두에 표시해 보십시오 .
hexdump -C FILE1.txt
E-ascii 또는 UTF-8로 코딩될 수 있습니다(참조:https://en.wikipedia.org/wiki/%C3%82#Character_mappings)
문제를 해결하려면 두 인코딩을 모두 일치시켜 보세요.
â in UTF-8 â in other encoding
| |
v v
sed 's/\xc3\xa2//' FILE1.txt | sed 's/\xE2//' > FILE2.txt
또 다른 해결책은 파일을 처리하기 전에 알려진 인코딩으로 변환하는 것입니다.
PROD 인코딩을 테스트하지 않는 것은 위험할 수 있습니다.
답변2
â
당신이 보고 있는 것은 거의 확실히 인코딩 문제이고 모든 줄이 대문자로 시작한다고 가정하기 때문에 다음을 시도해 볼 수 있습니다 .
LC_ALL=C sed 's/^[^A-Z]*//; s/ */;/g' FILE1.txt > FILE2
그러면 귀하의 문자 가 AZ 범위에 포함되지 않도록 C
보장하는 로케일을 사용하여 명령이 실행됩니다 . â
그런 다음 sed 명령은 단순히 각 줄의 시작 부분에서 AZ 범위에 없는 모든 문자를 제거한 다음 두 개 이상의 공백이 있는 모든 항목을 ;
.
답변3
노력하다
sed 's/^â//; s/ */;/g' FILE1.txt > FILE2.txt
그리고 그것이 당신에게 효과가 없다면 반대 투표하세요
답변4
각 줄의 첫 번째 문자를 제거하려면 다음과 같아야 합니다.
cut -c2- # not with the GNU implementation which is currently not multi-byte aware
sed 's/^.//'
awk '{print substr($0, 2)}' # note the 2 instead of 1 as offsets are 1-based
# not with mawk or other non-multi-byte aware awk
# implementations.
그러나 .
해당 â
문자를 일치시키고 substr()
제대로 작동하려면 â
로케일 인코딩에 따라 인코딩해야 합니다(의 출력 참조 locale charmap
).
첫 번째 문자를 제거하고 모든 공백 시퀀스를 로 바꾸려면 ;
다음 중 하나를 수행할 수 있습니다.
sed 's/^.//;s/[[:space:]]\{1,\}/;/g'
또는:
awk -v OFS=';' '{$0 = substr($0, 2); $1 = $1; print}'
(후자는 공백 문자로 끝나는 줄에 대한 후행을 포함하지 않으며 ;
구분 기호로 간주되는 공백 문자 목록은 구현 awk
및 로케일에 따라 다릅니다.)
이제 â
(U+00E2)가 iso8859-1 문자 집합(일명 latin1
기타 단일 바이트 문자 집합이라고도 함)에서 바이트 0xe2로 인코딩된다는 점도 주의하세요. 그리고 해당 바이트 0xe2는 여러 개의 3바이트 UTF-8 문자 인코딩의 첫 번째 바이트이기도 하며 그 중에는 여러 유니코드 공백 문자(예: U+2000 ~ U+200B 공백 문자)도 포함됩니다.
따라서 â
latin1 터미널에 가 표시되는 경우 입력에 실제로 UTF-8(0xe2 0x80 0x82)로 인코딩된 U+2002(EN SPACE)가 포함되어 있을 수 있으며 터미널에서는 이를 다음과 같이 표시 합니다 0xe2
. â
latin1에 없는 0x80 및 0x82에 대해서는 아무것도 표시되지 않습니다.
EN SPACE를 제거하려면 UTF-8 로케일인 문자 1개를 제거하거나 단일 바이트 로케일(예: latin1 또는 C 로케일을 사용하는 문자)에서 문자 3개를 제거해야 합니다.