옵션을 전달하지 않고 getopts를 감지하는 방법은 무엇입니까?

옵션을 전달하지 않고 getopts를 감지하는 방법은 무엇입니까?

이 코드가 있습니다 -

#getoptDemo.sh
usage()
{
    echo "usage: <command> options:<w|l|h>"
}
while getopts wlh: option
do
    case $option in
            (w)
                    name='1';;
            (l)
                    name='2';;
            (h)
                    name='3';;
            (*)
                    usage
                    exit;;
    esac
done
print 'hi'$name

(옵션 없이) 실행하면 함수를 호출하는 대신 bash getoptDemos.sh인쇄됩니다 . w, h, l 이외의 옵션이 제공되면 use를 호출합니다. 그러면 옵션이 지정되지 않으면 작동하지 않습니다.hiusage

?대신 을 사용해 보았지만 \?원하는 것을 얻을 수 없습니다. 내 말은 모든 것이 작동한다고 말합니다.:*docsgetopt?

내가 뭘 잘못했나요?

답변1

getopts옵션을 순서대로 진행하세요. 그것이 바로 그 일입니다. 사용자가 옵션을 전달하지 않으면 첫 번째 호출에서 getoptswhile 루프가 종료됩니다.

인수를 사용하는 옵션이 없으면 값은 OPTIND전달된 옵션 수를 나타냅니다. 일반적으로 말하면 OPTIND옵션이 아닌 인수(피연산자)가 아닌 옵션 또는 옵션 인수에 대한 인수의 개수입니다.

while getopts …; do …; done
if [ $OPTIND -eq 1 ]; then echo "No options were passed"; fi
shift $((OPTIND-1))
echo "$# non-option arguments"

어쨌든 옵션이 없는지 확인하려는 것이 아니라 name-setting 옵션이 전달되지 않은 경우입니다. 그래서설정되어 있지 않은지 확인 name하고 먼저 설정을 해제하세요..

답변2

옵션 없이 이 스크립트를 실행하면 getopt는 false를 반환하므로 루프에 전혀 들어가지 않습니다. 인쇄에만 해당됩니다. 이것이 ksh/zsh입니까?

옵션이 있어야 한다면 가장 좋은 방법은 루프 후에 $name을 테스트하는 것입니다.

if [ -z "$name" ]
then
   usage
   exit
fi

그러나 호출하기 전에 비어 있는지 확인하십시오 $name(쉘이 시작될 때 수신하는 환경에 하나가 있을 수 있기 때문입니다 getopts).$name

unset name

( getopts루프 전)

답변3

변수를 사용하여 확인하겠습니다. getopts가 인수 없이 루프를 통과하지 않는 경우 다음과 같이 사용할 수 있습니다.

#getoptDemo.sh
usage()
{
    echo "usage: <command> options:<w|l|h>"
}

no_args="true"
while getopts wlh: option
do
    case $option in
            (w)
                    name='1';;
            (l)
                    name='2';;
            (h)
                    name='3';;
            (*)
                    usage
                    exit;;
    esac
    no_args="false"
done

[[ "$no_args" == "true" ]] && { usage; exit 1; }

print 'hi'$name

답변4

getopts블록 앞에 $1(명령줄에 전달된 첫 번째 인수/옵션)이 빈 문자열과 같은지 확인하세요. 그렇다면 사용법 메시지를 인쇄하고 종료합니다(또는 무정부주의자라면 "옵션 없음" 기능을 수행합니다). 그렇지 않으면 getopts평소대로 옵션을 구문 분석해 보겠습니다.

이 기능이 getopts에 포함되지 않은 이유는 "if-else"를 사용하여 bash에서 이미 해당 기능을 수행할 수 있기 때문입니다. 예:

if [[ $1 == "" ]]; then
    Your_Usage_Function;
    exit;
else
   #parse options with getopts code block here;
fi

합리적인?

관련 정보