다음 표현식을 시도하면 bash
이상한 오류 메시지가 나타납니다.
[: -lt: unary operator expected
먼저 함수 정의
some_func () {
(( 3 + 5 ))
}
그리고 표현은
[ $(some_func) -lt 10 ] && true
-lt
문제는 명령 대체 및/또는 산술 확장과 같은 연산자를 혼합하는 것 같아요 .
종료 코드 $?
는 2이고 메시지는 다음과 같습니다.an unary op was expected
.
답변1
그것은해야한다
some_func() {
echo "$(( 3 + 5 ))"
}
[ "$(some_func)" -lt 10 ]
실패한 이유
$(some_func)
으로 확장됩니다.산출그러나 아무것도 출력하지 않는 함수*(후행 개행 제외). 따라서 테스트는
[ -lt 10 ]
가장 기본적인 형태로는,테스트 [
에서는 1~3개의 매개변수를 허용합니다.. 위에는 2개의 매개변수가 있으므로 Bash는 첫 번째 매개변수가 단항 연산자일 것으로 예상합니다. -lt
바이너리이므로 오류 메시지가 나타납니다.
당신이 있었다적절하게 확장을 인용했습니다.~와 함께
[ "$(some_func)" -lt 10 ]
테스트에 빈 문자열이 있으므로 오류는 "정수 표현식 예상"입니다.
[ "" -lt 10 ]
그리고 아래가 아닌 이상사소하지 않은 상황, && true
중복됩니다.
*확장은 인용되지 않았기 때문에 출력도 진행됩니다.단어 분리그리고파일 이름 확장. $IFS
기본값에서 변경되지 않은 한 이는 현재 예에서 역할을 하지 않아야 합니다 .
답변2
$(cmd)
얻는다표준 출력¹ 의 cmd
결과로 확장하려면 다음을 수행해야 합니다 cmd
.산출그것:
some_func() {
echo "$(( 3 + 5 ))"
}
[ "$(some_func)" -lt 10 ]
다른 사람들이 이미 말했듯이. 그러나 이는 some_func
하위 쉘 환경에서 실행되므로 변수 또는 기타 사항에 대한 수정 사항은 이후에 손실됩니다.
예를 들어, 다음을 수행하는 것은 의미가 없습니다.
counter=0
incr() { echo "$((++counter))"; }
while [ "$(incr)" -le 10 ]...
as는 $(incr)
항상 1로 확장됩니다( counter
서브쉘에서만 증가됩니다).
함수가 수치 결과를 반환하는 경우산술 평가, 다음을 지원하는 쉘이 필요합니다.수학 함수또는 .ksh93
하지 않습니다.zsh
bash
안에 zsh
:
counter=0
incr() (( ++counter ))
functions -M incr
while (( incr() <= 10 )); do
print $counter
done
안에 ksh93
:
function .sh.math.incr i {
# ksh93 functions must take at least one argument
(( .sh.value = (counter += i) ))
}
while (( incr(1) <= 10 )); do
print "$counter"
done
ksh93 또는 최신 버전의 mksh의 또 다른 대안은 하위 쉘을 도입하지 않는 명령 대체 형식을 사용하는 것입니다.
counter=0
function incr { print "$(( ++counter ))"; }
while [ "${ incr; }" -le 10 ]; do
print "$counter"
done
또는 mksh
:
counter=0
incr() (( REPLY = ++counter ))
while [ "${| incr; }" -le 10 ]; do
print "$counter"
done
을 포함한 모든 POSIX 셸에서는 bash
항상 미리 정의된 변수( $REPLY
일반적으로 사용되는 변수)의 값을 반환할 수 있습니다.
counter=0
incr() { REPLY=$(( counter += 1 )); }
while incr; [ "$REPLY" -le 10 ]; do
echo "$counter"
done
자세한 내용은 다음에서 확인할 수 있습니다.mksh의 valsub 기능에 대한 다른 Q&A에 대한 답변입니다.
¹ 후행 개행 문자가 제거되고 NUL 문자의 경우 bash
따옴표를 잊어버렸기 때문에 여기서는 분할+글로브에 따라 달라질 수 있습니다.
답변3
명령 대체출력을 캡처합니다.명령이나 기능의. 해당 함수에는 출력이 없습니다.
변수 $?
는반환 코드기능의.
다음 중 하나를 수행하십시오.
some_func
(( $? < 10 )) && echo yes
또는 기능을 다음으로 변경하십시오.
some_func() {
echo $(( 3 + 5 ))
}
[[ $(some_func) -lt 10 ]] && echo yes
[[...]]
대신에 내가 어떻게 사용하고 있는지 확인하세요 [...]
. 조건부 이중 괄호는 빈 값에 대해 더 관대합니다.