이 줄이 출력을 생성하지 못하는 이유는 무엇입니까? [복사]

이 줄이 출력을 생성하지 못하는 이유는 무엇입니까? [복사]

다음은 bash에서 결과를 생성하지 않습니다.

while true ; do upower -d ; sleep 1 ; done | grep percentage | uniq

나는 체인의 마지막 프로그램이 무엇인지, 심지어 마지막에서 두 번째 프로그램이 무엇인지는 중요하지 않다는 것을 발견했습니다. 두 번째 프로그램은 항상 예상한 출력을 생성하는 반면, 마지막 프로그램은 항상 결과를 생성하지 못합니다.

( while ... done )while 루프를 서브셸(통과)에 래핑하거나 마지막 명령을 제외한 모든 것을 서브셸에 래핑하고 마지막 명령으로 파이프하는 것도 중요하지 않은 것 같습니다.

나는 이 행동으로 인해 매우 혼란스러워졌습니다.

내 직감이 말해주는데...

...읽기 및 쓰기를 차단하여 체인에 일종의 I/O 교착 상태가 발생하고 while 루프가 항상 출력을 생성하지는 않습니다. 하지만 반면에 저는 이전에도 아무 문제 없이 이 작업을 여러 번 해왔습니다. 게다가 이런 경우에는 while 루프와 다음 명령 사이에 문제가 있는 것 아닌가요? 그래서 나는 혼란스러워요. 다른 사람이 재현할 수 없는 경우 bash 버전 정보를 제공합니다.

즉시 명확하지 않은 경우 ...

이 코드 줄의 요점은 배터리 비율의 모든 변경 사항을 인쇄하지만 새 배터리 수준만 인쇄하는 것입니다. 폴링을 사용합니다. 나는 달리는 것만으로도 같은 행동을 할 것이라고 생각합니다.

upower --monitor-detail | grep percentage | uniq

하지만 이것은 일회성 일이었고 위의 방법이 실패하기 시작할 때까지 나는 그것에 대해 5 초 이상 생각할 생각이 없었습니다. 이것은 흥미로운 질문이 되는 때입니다. 또한 모니터 세부 정보가 뒤에서 폴링되고 있는지도 모르겠습니다(그리고 확인하기 위해 strace를 실행하지도 않았습니다).

편집하다:분명히 위 버전도 --monitor-detail아무것도 생성하지 않았거나 적어도 그렇게 보였습니다. 폴링/업데이트 빈도가 상당히 드물었기 때문에 아마도 오래 기다리지 않았을 것입니다.알다나는 원래 질문을 충분히 기다렸습니다). 지금 저는 매우 혼란스럽습니다. 결국 그 strace를 실행해야 할 것 같아요 ...

답변1

를 사용해야 합니다 . 그렇지 않으면 표준 출력 버퍼가 출력을 채우는 grep --line-buffered percentage데 오랜 시간이 걸립니다 .grep

답변2

Marco d'Itri의 답변 외에도 모든 도구가 사용자 정의 버퍼링을 지원하는 것은 아닙니다. 실행 중인 도구가 이 작업을 수행하지 않거나 사용자 정의 버퍼 크기로 실행하려는 경우 stdbuf도구의 버퍼링 동작을 재정의할 수 있습니다. 예를 들어 이 경우 출력을 라인 버퍼링하도록 합니다.

while true ; do upower -d ; sleep 1 ; done | stdbuf -oL grep 'percentage' | uniq

출력을 버퍼링 해제하도록 강제합니다.

while true ; do upower -d ; sleep 1 ; done | stdbuf -o0 grep 'percentage' | uniq

출력을 512B 단위로 버퍼링하도록 강제합니다.

while true ; do upower -d ; sleep 1 ; done | stdbuf -o512 grep 'percentage' | uniq

K, M, G, [...]를 추가하여 KB, MB, GB, [...] 단위로 출력을 지정할 수 있습니다.

while true ; do upower -d ; sleep 1 ; done | stdbuf -o512K grep 'percentage' | uniq

답변3

POSIX에서는 sedrite 명령을 사용하여 라인 버퍼 출력을 얻을 수 있습니다 w.

while  sleep 1
do     upower -d
done | 
sed -n /percentage/w\ /dev/fd/1 |
uniq

... /dev/fd/[num]연결을 지원하는 시스템에서 작동 합니다.(예: 거의 모든 Linux 시스템)

하지만 다음과 같이 할 수 있습니다.

while  sleep 1
do     upower -d
done | 
sed '/percentage/!d;H;x
     /^\(.*\)\n\1$/d;g'

위의 내용은 이 작업을 수행해야 합니다. 이는 단지 작은 스크립트 uniq의 기능을 래핑할 뿐입니다 .grepsed

관련 정보