オプションを渡さずに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(シェルの起動時に受け取る環境に1つがある可能性があるため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

合理的な?

関連情報