Bash 스크립트를 사용하여 파일에 대한 일부 텍스트 처리를 수행하려고 합니다. 목표는 'attribute:' 라벨 아래에 들여쓰기된 "field:"로 시작하는 모든 줄을 가져와서 그 뒤에 나오는 "- attr:"로 시작하는 관련 줄로 바꾸는 것입니다.
지금까지 레이블과 일치해야 하는 정규식 패턴이 있다고 생각합니다.
/ *field:(.*)/g
/ *- attr:(.*)/g
그러나 원하는 필드를 구문 분석하고 올바르게 교체하는 논리에는 성공하지 못했습니다.
입력 텍스트 예
- metric: 'example.metric.1'
attributes:
field: 'example 1'
- attr: 'example1'
field: 'example 2'
- attr: 'example2'
field: 'example 3'
- attr: 'example3'
field: 'example 4'
- attr: 'example4'
- metric: 'example.metric.2'
attributes:
field: 'example 5'
- attr: 'example5'
field: 'example 6'
- attr: 'example6'
field: 'example 7'
- attr: 'example7'
- metric: 'example.metric.3'
...
원하는 출력
- metric: 'example.metric.1'
attributes:
- attr: 'example1'
field: 'example 1'
- attr: 'example2'
field: 'example 2'
- attr: 'example3'
field: 'example 3'
- attr: 'example4'
field: 'example 4'
- metric: 'example.metric.2'
attributes:
- attr: 'example5'
field: 'example 5'
- attr: 'example6'
field: 'example 6'
- attr: 'example7'
field: 'example 7'
- metric: 'example.metric.3'
...
이 작업을 수행하려면 어떻게 해야 합니까?
답변1
모든 Unix 상자의 모든 쉘에서 awk를 사용하십시오.
$ awk '$1=="field:"{s=ORS $0; next} {print $0 s; s=""}' file
- metric: 'example.metric.1'
attributes:
- attr: 'example1'
field: 'example 1'
- attr: 'example2'
field: 'example 2'
- attr: 'example3'
field: 'example 3'
- attr: 'example4'
field: 'example 4'
- metric: 'example.metric.2'
attributes:
- attr: 'example5'
field: 'example 5'
- attr: 'example6'
field: 'example 6'
- attr: 'example7'
field: 'example 7'
- metric: 'example.metric.3'
일부 줄 뒤에 공백이 없거나 field:
어떤 이유로 정규식을 사용하고 싶은 욕구가 있다면 또는 중 원하는 것으로 $1=="field:"
변경 하세요.$1~/^field:/
/^[[:space:]]*field:/
답변2
와 함께 sed
:
sed -n '/^ *field: /{h;n;G};p' data
키워드 가 일치하면 field
다음과 같습니다.
- 현재 줄을
hold space
(h
) 안에 저장 pattern space
(n
) 안의 파일에서 다음 줄을 가져옵니다.- ( )
pattern space
로 교환 (라인 교환과 동일)hold space
G
만나는 각 줄을 인쇄하십시오.p
답변3
사용 awk
:
awk '{if ($1 == "field:") {a=$0;x=0}
else if (/- attr:/) {$0 = $0 ORS a; x=1} else {x=1}}x' input
이 명령에서 가 field:
발견되면 현재 입력 레코드( $0
)가 변수에 저장되고 a
x는 0으로 설정됩니다. 그리고 attr:
가 발견 되면 $0
d를 old로 변경 $0
하고 그 뒤에 ORS
(newline) 다음에 변수를 붙입니다 a
.
답변4
POSIX sed 구성을 사용하여 해당 라인을 뒤집을 수 있습니다.
sed '/attr:/!x;$G' file