Bash의 부울 테스트 && 및 || 관련 문제

Bash의 부울 테스트 && 및 || 관련 문제

다음을 고려하세요:

root@debian-lap:/tmp echo "Step 1 " || echo "Failed to execute step 1" ; echo "Step 2"
Step 1
Step 2
root@debian-lap:/tmp

echo1번째와 3번째 명령이 정상적으로 실행되는 것을 볼 수 있다 .

첫 번째 명령이 실패하면 스크립트를 중지하고 다음에서 중지하고 싶습니다 exit.

root@debian-lap:/home/fugitive echo "Step 1 " || echo "Failed to execute step 1" && exit 2 ; echo "Step 2"
Step 1 
exit
fugitive@debian-lap:~$ 

exit명령은 첫 번째 명령의 종료 코드가 0이더라도 셸을 실행하고 종료합니다. 내 질문은 – 왜?

번역하면 다음을 의미하지 않습니다.

  • 에코 "1단계"
  • 명령이 실패하면 '1단계를 수행할 수 없습니다'를 에코하고 스크립트를 종료합니다.
  • 그렇지 않으면 "2단계"가 에코됩니다.

확인 해봐:

cmd foo1 || cmd foo2 && exit

cmd foo2 and (&&) exit실패시에만 실행하면 안되나요 cmd foo1?

내가 무엇을 놓치고 있나요?

편집하다

제가 정말로 하고 싶은 두 번째 예를 추가하겠습니다(여전히 더미 테스트입니다).

root@debian-lap:/tmp/bashtest a="$(ls)" || echo "Failed" ; echo $a
test_file  # < - This is OK
root@debian-lap:


root@debian-lap:/tmp/bashtest a="$(ls)" || echo "Unable to assign the variable" && exit 2; echo $a
exit
fugitive@debian-lap:~$   # <- this is confusing part

root@debian-lap:/tmp/bashtest a="$(ls /tmpppp/notexist)" || echo "Unable to assign the variable" ; echo $a
ls: cannot access /tmpppp/notexist: No such file or directory
Unable to assign the variable            # <- This is also OK
root@debian-lap:

답변1

마지막으로 실행한 명령( echo)이 성공했기 때문입니다. 명령을 그룹화하려면 다음 명령문을 사용하는 것이 더 명확합니다 if.

if ! step 1 ; then
   echo >&2 "Failed to execute step 1"
   exit 2
fi

오류 메시지를 그룹화하고 종료할 수도 있지만 { ... }읽기가 약간 어렵습니다. 그러나 이는 종료 상태의 정확한 값을 유지합니다.

step 1 || { echo >&2 "step 1 failed with code: $?"; exit 2; }

&&오류 메시지와 함께 실패하더라도 종료하고 싶다고 가정하고 있으므로 이를 세미콜론으로 변경했습니다 (그리고 모범 사례를 위해 이러한 오류를 stderr에 출력함).

종료 상태를 유지하는 변형 의 경우 이 섹션 if에 코드를 추가해야 합니다 .else

if step 1; then
  : OK, do nothing
else
  echo >&2 "step 1 failed with code: $?"
  exit 2
fi

(이것은 키워드 없이 Bourne 쉘과도 호환됩니다 !).


또는 왜 명령 그룹이 이것을 좋아하는지,표준이론:

AND-OR 목록은 AND 연산자로 구분된 하나 이상의 파이프 시퀀스입니다 "&&"."||"

연산자 "&&""||"는 동일한 우선순위를 가져야 하며 왼쪽 연관성을 평가해야 합니다.

즉, like 는 and 가 먼저 결합된 somecmd || echo && exit것처럼 동작합니다 . 즉, and not 입니다 .somecmdecho{ somecmd || echo; } && exitsomecmd || { echo && exit; }

답변2

문제는 이진/논리 연산자의 우선순위에 있다고 생각합니다. 즉, "and"와 "or"는 동일한 우선순위를 가지므로 다음 줄은
echo "Step 1 " || echo "Failed to execute step 1" && exit 2 ; echo "Step 2"본질적으로 다음과 같습니다:
( echo "Step 1 " || echo "Failed to execute step 1" ) && exit 2 ; echo "Step 2".
당신은 그것을 시도해야합니다 echo "Step 1 " || ( echo "Failed to execute step 1" && exit 2 ) ; echo "Step 2".

관련 정보