예상되는 정수 표현식을 얻는 이유는 무엇입니까?

예상되는 정수 표현식을 얻는 이유는 무엇입니까?

그래서 학습 경험으로 bash에서 메뉴 시스템을 만들어 보았습니다. 이 작업을 수행할 수 있는 방법은 셀 수 없이 많으며 심지어 "더 나은" 방법도 있을 것이라고 확신합니다. 하지만 제가 가진 방법은 다음과 같습니다.

echo "
2nd Menu
********
1) command
2) command
M) Main menu
X) Exit program
"
read -p "Choose option >" opt
if [ "$opt" -eq 1 ]; then
    commands
elif [ "$opt" -eq 2 ]; then
    commands
elif [[ "$opt" = [m,M] ]]; then
    main #calls the function main()
elif [[ "$opt" = [x,X] ]]; then
    exit
else
    echo "Invalid option"
    main
fi

이 스크립트는 "X) 프로그램 종료"를 제외한 모든 옵션에서 작동합니다. "X" 또는 "x"를 실행하면 이 오류가 발생합니다...

./acct-mgr.sh: line 10: [: x: integer expression expected
./acct-mgr.sh: line 12: [: x: integer expression expected
Invalid option

이것은 나를 혼란스럽게 한다! 나는 각 데이터 유형(정수의 경우 -eq, 문자열의 경우 =)에 대해 올바른 비교 연산자를 사용하고 있으며 "x"를 제외한 모든 옵션이 작동한다고 확신합니다.

어떤 도움이라도 대단히 감사하겠습니다. 감사해요.

추신 - 원하는 결과를 얻을 수 있는 다른 방법을 알려주시면 감사하겠습니다. 하지만 그럼에도 불구하고 이것이 왜 제 경험적 방법에는 적용되지 않는지 알고 싶습니다. 다시 한 번 감사드립니다.

답변1

M/m 또는 X/x를 입력하면 숫자가 아닌 숫자를 숫자와 비교하므로 -eq오류가 발생합니다. 가끔 문자열이 되고 싶다면 $opt항상 문자열로 처리하세요.

...
if [ "$opt" = "1" ]; then
    commands
elif [ "$opt" = "2" ]; then
    commands
...

답변2

보충제로@앤디가 이미 말했어요, 알아채다

[[ "$opt" = [m,M] ]]

m, 및 .,​ 일치 하고 일치만 M하고 싶다면 다음과 같습니다.mM

[[ "$opt" = [mM] ]]

여기서는 표준 구성을 사용하겠습니다 case.

case $opt in
  (1)   commands;;
  (2)   commands;;
  (m|M) main;;
  (x|X) exit;;
  (*)   echo >&2 "Invalid option"; main
esac

또한 의 동작은 의 read현재 값에 따라 달라집니다 $IFS. 사용자로부터 행을 읽으려면 다음을 사용할 수 있습니다.

IFS= read -r opt

문자 읽기:

IFS= read -rn1 opt

가서 하나 읽어봐단어(한 줄을 읽으되 선행 공백과 탭 및 첫 번째 단어를 제외한 모든 항목은 무시합니다):

IFS=$' \t' read -r opt ignored

또는 다음에서 사용을 허용합니다.단어백슬래시 접두사를 추가하면 다음과 같습니다.

IFS=$' \t' read opt ignored

관련 정보