가끔 추가 줄바꿈이 포함된 입력 파일을 읽는 방법은 무엇입니까?

가끔 추가 줄바꿈이 포함된 입력 파일을 읽는 방법은 무엇입니까?

대부분의 경우 다음과 같은 입력 파일을 얻습니다.

java-1.8.0-openjdk.x86_64  1:1.8.0.232.b09-1.el6_10        asyum:ol6_latest
java-1.8.0-openjdk-headless.x86_64 1:1.8.0.232.b09-1.el6_10        asyum:ol6_latest
kernel.x86_64              2.6.32-754.23.1.el6             asyum:ol6_latest

...while 루프가 있고 다음 코드를 사용하여 각 행에 대해 field1과 field2를 성공적으로 캡처할 수 있습니다.

f1=$(echo $line | awk '{print $1}')
f2=$(echo $line | awk '{print $2}')

그러나 때때로 다음과 유사한 입력 파일이 표시됩니다.

java-1.8.0-openjdk.x86_64  1:1.8.0.232.b09-1.el6_10        asyum:ol6_latest
java-1.8.0-openjdk-headless.x86_64
                           1:1.8.0.232.b09-1.el6_10        asyum:ol6_latest
kernel.x86_64              2.6.32-754.23.1.el6             asyum:ol6_latest

(라인 2를 구분하는 추가 줄바꿈이 있다는 점에 유의하세요.)

이러한 유형의 입력을 프로그래밍 방식으로 처리하기 위한 팁/요령이 있습니까(입력 파일을 수동으로 정리하는 대신)?

답변1

다음은 선행 공백에만 의존하는 솔루션입니다. 예상되는 필드 수에 의존하지 않습니다.

이것GNU 매뉴얼sed"공백으로 시작하는 줄을 연결하는" 방법을 제공합니다.

sed -E ':a ; $!N ; s/\n\s+/ / ; ta ; P ; D'

매뉴얼에서는 이식 가능한(GNU가 아닌) 변형이 다음과 같다고 주장합니다.

sed -e :a -e '$!N;s/\n  */ /;ta' -e 'P;D'

답변2

이렇게 하면 원하는 효과를 얻을 수 있습니다.

#!/usr/bin/env bash

while read line; do
    declare -a array=($line)
    if  test ${#array[@]} != 3; then
        read line2
        array+=($line2)
    fi
    f1=${array[0]}
    f2=${array[1]}
    echo $f1 $f2
done

run with : test.sh < inputfile

행에 세 개의 항목이 포함되어 있는지 확인하고 그렇지 않은 경우 다음 행을 조인합니다.

답변3

어쨌든 그것을 사용하고 있으니 awk전적으로 의존하는 것은 어떨까요? 노력하다

read f1 f2 <<< $(awk '{while (NF < 3) {getline X; $0 = $0 FS X};  print $1, $2}' file)

답변4

입력 데이터의 올바른 형식의 각 행이 세 단어(여기서는 공백 문자를 포함하지 않는 문자열로 느슨하게 정의됨)로 구성된다고 가정하면 입력 데이터를 전처리할 수 있습니다.

<input_file tr -s '[:blank:]' '\n' | paste - - - | column -t

<newline>여기서는 모든 공백 문자(문자 포함)를 단일 로 바꾸고 <newline>, 결과를 세 단어 줄로 재배치하고, 출력 형식을 깔끔하게 지정합니다. 마지막 단계는 귀하의 질문을 고려할 때 불필요한 장식 단계입니다.

관련 정보