반면 file
:
2018-03-22 foo/bar/baz
2020-09-30 Lorem/ipsum/dolor
2021-10-01 yadda/yadda/yadda
2022-03-14 blah/blah/blah
(실제 파일에는 이와 같은 수천 줄이 포함되어 있습니다)
문자열을 얻는 방법2018-03-22_2022-03-14
? 이는 레코드 1의 필드 1, 밑줄, 마지막 레코드의 필드 1을 연결한 것입니다.
나는 이것을 생각해 냈습니다 :
$ awk 'BEGIN{ORS="_"}NR==1{print $1} END{print $1}' file | sed 's/_$//'
2018-03-22_2022-03-14
작동하지만복잡하지 않은awk
sed
파이프나 서브쉘 만 사용하거나 사용하지 않고 동일한 결과를 얻는 방법입니다. 실제로 그런 방법이 있나요?
답변1
전용 버전 sed
:
sed 's/ .*//;1h;$!d;H;g;y/\n/_/' file
s/ .*//
공백 뒤의 모든 항목을 제거하고 날짜만 유지하는 데 사용됩니다 .1h
1
공백 에 행 날짜 복사hold
$!d
d
마지막 줄을 제외한 모든 줄 삭제- 여기에 도착하면 마지막 행에 있으므로
H
첫 번째 날짜가 포함된 이 행을 이전 공간에 추가한 다음 둘 다 패턴 공간에 복사합니다.g
- 이제 남은 유일한 일은 삽입된 개행(추가로 인해)을 밑줄로 바꾸는 것입니다.
y/\n/_/
(네 좀 짧네요)
답변2
이식성을 위해 이 섹션에서 구현 print $1
(또는 사용 $anything
) 하지 마십시오 END
. 이 섹션의 해당 항목은 $0
POSIX에 따라 정의되지 않은 동작이기 때문입니다. 일부 awks에서는 이 부분이 마지막 줄에서 읽은 첫 번째 필드의 값이 되고, 다른 경우에는 null이 되며, 다른 경우에는 다른 값일 수 있습니다.$1
END
$1
END
모든 Unix 시스템의 모든 쉘에서 awk를 사용하십시오.
$ awk -v OFS='_' 'NR==1{beg=$1} {end=$1} END{print beg, end}' file
2018-03-22_2022-03-14
_
또는 입력 파일이 비어 있으면 단일 파일을 인쇄하지 마세요.
awk -v OFS='_' 'NR==1{beg=$1} {end=$1} END{ if (NR) print beg, end}' file
위의 내용은 입력에 행이 1개만 있는 경우 해당 $1
행 간에 동일한 값이 반복되기를 원한다고 가정합니다 _
. 이것이 원하는 것이 아니라면 질문을 업데이트하여 이 사례에 대한 요구 사항을 명확히 하십시오.
답변3
출력 제어 의 경우 printf
:
$ awk 'NR==1{printf("%s_", $1)}END{print $1}' f
2018-03-22_2022-03-14
답변4
대용량 파일을 처리하는 데 속도 가 느리기 때문에 대용량 입력 파일을 사용 head
하는 것이 좋습니다 .tail
awk
sed
$ cat input.txt
2018-03-22 foo/bar/baz
2020-09-30 Lorem/ipsum/dolor
2021-10-01 yadda/yadda/yadda
2022-03-14 blah/blah/blah
{ head -n1 input.txt && tail -n1 input.txt; } |
cut -d ' ' -f1 | paste -sd _ -
2018-03-22_2022-03-14