'IFS'로 '읽기'가 공백 문자를 병합하지 못하도록하려면 어떻게해야합니까? [복제]

Nov 26 2020

다음으로 구분 된 데이터를 읽는이 코드 조각을 가져옵니다. |

DATA1="Andreas|Sweden|27"
DATA2="JohnDoe||30"   # <---- UNKNOWN COUNTRY
while IFS="|" read -r NAME COUNTRY AGE; do 
    echo "NAME:    $NAME"; echo "COUNTRY: $COUNTRY";
    echo "AGE:     $AGE"; done<<<"$DATA2"

산출:

이름 : JohnDoe
국가 :
나이 : 30

그것은 작동합니다 동일하게 바로 사용하여, 우리는 똑같은 일을하고있는이 코드 조각에 \t대신 구분 기호로|

DATA1="Andreas  Sweden  27"
DATA2="JohnDoe      30"  # <---- THERE ARE TWO TABS HERE
while IFS=$'\t' read -r NAME COUNTRY AGE; do echo "NAME: $NAME";
    echo "COUNTRY: $COUNTRY"; echo "AGE: $AGE";
done<<<"$DATA2"

하지만 그렇지 않습니다.

산출:

이름 : JohnDoe
국가 : 30 세
:

Bash 또는 read또는 IFS코드의 다른 부분이 의도하지 않은 공백을 함께 뭉칩니다. 왜 이런 일이 발생하며 어떻게 해결할 수 있습니까?

답변

3 fpmurphy Nov 26 2020 at 11:00

bash제대로 작동합니다. 로부터 bash문서 :

쉘은 IFS의 각 문자를 구분 기호로 취급하고 다른 확장의 결과를 이러한 문자의 단어로 분할합니다. IFS가 설정되지 않았거나 해당 값이 정확히 <space><tab><newline>, 기본값 인 <space>경우 <tab>, 및<newline>이전 확장 결과의 시작과 끝 부분은 무시되고 시작 또는 끝 부분에없는 IFS 문자 시퀀스는 단어를 구분하는 역할을합니다. IFS에 기본값이 아닌 값이있는 경우 공백 문자가 IFS (IFS 공백 문자) 값에있는 한 단어의 시작과 끝에서 공백 문자 공백 및 탭의 시퀀스는 무시됩니다. IFS 공백이 아닌 IFS의 모든 문자는 인접한 IFS 공백 문자와 함께 필드를 구분합니다. 일련의 IFS 공백 문자도 구분 기호로 처리됩니다.

이 "기능"을 극복하기 위해 다음과 같은 작업을 수행 할 수 있습니다.

#!/bin/bash

DATA1="Andreas  Sweden  27"
DATA2="JohnDoe          30"  # <---- THERE ARE TWO TABS HERE

echo "$DATA2" | sed 's/\t/;/g' | while IFS=';' read -r NAME COUNTRY AGE; do echo "NAME: $NAME"
    echo "COUNTRY: $COUNTRY" echo "AGE: $AGE"
done