입력이 비어 있어서는 안 되며 쉘 스크립트의 while 루프에 숫자만 포함해야 하는 다중 조건 검사를 수행하려고 하는데 이를 시도하는 동안 여러 오류가 발생합니다. 여러 옵션을 시도했고 Unix Stackexchange 및 Stack Overflow에서 이 문제에 대한 여러 질문을 보았지만 그 중 어느 것도 도움이 되지 않았습니다. 그래서 이 질문을 여기에 게시합니다. 옵션 1:
while [ \( -z "$account_number" \) && \( "$account_number" =~ "^[0-9]+$" \) ];
do printf 'Input account Number RWDEx: '
read -r account_number
[ -z "$account_number" ] && echo 'Account Number cannot be empty; try again.'
done
[: Missing `]' 오류가 발생합니다. 많은 사람들이 조건과 괄호 사이의 공백 문제 때문에 이 오류를 제안했지만 작동하지 않습니다.
옵션 2:
while [[ -z "$account_number" && "$account_number" =~ "^[0-9]+$" ]]
do printf 'Input account Number RWDEx: '
read -r account_number
[ -z "$account_number" ] && echo 'Account Number cannot be empty; try again.'
done
위의 조건을 주면 입력을 요구하지도 않습니다.
이 문제를 해결하는 데 도움을 주세요. 저는 #!/bin/bash를 사용하고 있습니다. 스크립트를 #!/bin/bash 대신 /bin/bash로 변경해 보았습니다.
답변1
그냥 사용:
#! /bin/bash -
n=
pattern='^(0+|[123456789][0123456789]*)$' # decimal integer number,
# exclude 0123 octals
until [[ $n =~ $pattern ]]; do
IFS= read -rp 'Enter a decimal number: ' n || exit # exit upon EOF
done
또는:
#! /bin/bash -
pattern='^(0+|[123456789][0123456789]*)$' # decimal integer number,
# exclude 0123 octals
while true; do
IFS= read -rp 'Enter a decimal number: ' n || exit # exit upon EOF
if [ -z "$n" ]; then
echo >&2 "Cannot be empty, try again"
elif [[ ! $n =~ $pattern ]]; then
echo >&2 "Not a decimal integer number, try again"
else
break
fi
done
또는 더 나은 방법은 표준 sh
구문을 사용하는 것입니다. 그러면 다음이 필요하지 않습니다 bash
.
#! /bin/sh -
while true; do
printf >&2 'Enter a number: '
IFS= read -r n || exit # exit upon EOF
case $n in
("")
echo >&2 "Cannot be empty, try again";;
(*[!0123456789]* | 0*[!0]*)
echo >&2 "Not a decimal integer number, try again";;
(*)
break;; # OK
esac
done
이것은 [
내장 쉘이라는 점에 유의하십시오. [
of는 연산자 bash
의 반대 zsh
이거나 연산자를 yash
지원하지 않습니다 .=~
또한 이렇게 하면 [ x && y ]
구문 분석되므로 cmd1 arg && cmd2 arg2
실행하고 [ x
성공하면 실행하세요 y ]
.
[[ ... ]]
반면에 내부적으로 &&
도 형식 인 특수 쉘 구조(ksh의)가 있습니다.그리고운영자.
그러나 다음과 같이 작성하면:
[[ -z $var && $var =~ ^[0-9]+$ ]]
$var
이는 null( )과 일치 여부 를 테스트하는 것으로 -z
, ^[0-9]+$
이는 불가능합니다.
내 생각에 당신은 다음을 의미한다고 생각합니다 :
[[ -z $var || ! $var =~ ^[0-9]+$ ]]
그러나 일치하는 경우 (0-9 범위의 하나 이상의 문자) -z $var
비어 있을 수 없으므로 중복 됩니다.$var
^[0-9]+$
대부분의 시스템의 대부분의 로케일에서 일치하는 항목 은 [0-9]
다소 무작위이므로 [0123456789]
소수점 이하 자릿수를 일치시키려면 를 사용하십시오.
와 같은 쉘에서는 bash
일반적으로 앞에 0이 있는 숫자를 제외하는 것이 좋습니다. 왜냐하면 숫자는 8진수로 해석되는 경향이 있기 때문입니다(예: 8의 경우 010).
bash
' 와 같은 사용자 프롬프트는 read -p
명령의 일반 출력(스크립트 출력)의 일부가 아니기 때문에 일반적으로 stderr에서 생성됩니다.생산하다그렇다면 다른 명령으로 파이프할 수 있습니다.)