다음과 같은 줄이 포함된 파일이 있습니다.
x
y
내가 달릴 때
grep -E "x$" filename.txt
아무것도 일치하지 않습니다. vi가 ^M
대부분의 행 끝에 표시되는 것처럼 , 문제는 Dos와 Unix 개행 문자 및 grep이 혼합되어 형식을 자동으로 감지하는 것이라고 추측됩니다.
나는 노력했다
grep --color=never -E "x.$" filename.txt
\r
줄 끝의 추가 항목과 일치하면 작동하지만 단일 문자를 인쇄 \r
하므로 --color=always
터미널 제어 문자를 추가할 때 깨집니다.
\r\n$
나에게 필요한 것은 및 를 \n
일치시키는 옵션입니다 $
.
샘플 파일의 16진수 덤프:
00000000 78 78 78 78 78 78 78 78 78 78 78 78 78 78 78 78 |xxxxxxxxxxxxxxxxx| 00000010 78 78 78 78 78 78 78 78 78 78 780d 0a790a |xxxxxxxxxxxx..y.|
DOS 라인 종결자와 Unix 라인 종결자를 볼 수 있습니다. 이 줄을 인쇄할 때 출력은 grep -E --color=always "x.$"
비어 있는 것으로 나타나며 일치하는 캐리지 리턴이 grep -E --color=never "x.$"
포함될 수 있습니다 .\r
.
답변1
GNU를 사용하는 경우 PCRE의 기호를 grep
사용하여 공백을 일치시킬 수 있으므로 0개 이상의 공백 문자가 일치됩니다.\s
\s*
$ printf 'x\r\nxx\n' > file
$ grep --color=no -P 'x\s*$' file
xx
빈 줄처럼 보이는 것은 실제로는 비어 있지 않습니다. 이로 인해 \r
터미널이 뒤로 이동하여 x
* 를 덮어쓰게 됩니다 . 다음을 통해 실제로 작동하는 모습을 볼 수 있습니다 od
.
$ grep -P 'x\s*$' file | od -c
0000000 x \r \n x x \n
0000006
GNU가 없으면 같은 방식으로 grep
POSIX 문자 클래스를 사용할 수 있습니다.[:space:]
$ grep 'x[[:space:]]*$' file | od -c
0000000 x \r \n x x \n
0000006
또는 다음과 같은 표준 도구를 사용하면 \r
제거도 쉽습니다 .tr
sed
$ tr -d '\r' < file | grep 'x$'
$ tr -d '\r' < file | grep 'x$'
x
xx
$ sed 's/\r//' file | grep 'x$'
x
xx
* 설명드린대로 참고해주세요@dave_thompson-085grep
, 이것은 별칭이 있기 때문에 발생합니다 . grep --color=auto
이는 색상 코드가 주변에 인쇄됨을 의미합니다 x
. x
이로 인해 \r
터미널이 커서를 뒤로 이동하게 되므로 x
나중에 인쇄되지 않는 색상 이스케이프에 의해 덮어쓰게 됩니다. 암호.
답변2
나에게 필요한 것은 \r\n$과 \nwith$`를 일치시키는 옵션입니다.
다음을 수행할 수 있습니다.
$ grep 'x^M\?$' infile
"^M"을 입력하려면 ctrl
키를 누른 상태에서 키를 누른 V
다음 ctrl
다시 키를 누르고 M
명령줄을 눌러야 합니다. A가 ^M
나타나서 한 carriage return
문자를 인코딩합니다.
grep의 출력은아직carriage return
터미널에 인쇄 위치를 줄의 시작 부분으로 되돌리고 거기에서 계속 인쇄하도록 지시하는 문자가 포함되어 있습니다 . 이는 이상한 결과를 초래할 수 있습니다.
정리 파일을 사용하는 것이 좋습니다 dos2unix
.
dos2unix infile >clean.infile
또는 (예를 들어, 파일을 분류하지 말고 dos2unix가 직접 읽을 수 있습니다):
cat infile | dos2unix | grep 'x$'