$1
は最初の引数です。$@
はすべてです。
シェルスクリプトに渡された最後の引数を見つけるにはどうすればよいですか?
これはちょっとしたハックです。
for last; do true; done
echo $last
これも非常に移植性が高く(再び、bash、ksh、shで動作するはずです)、引数をシフトしません。
ループする対象を指定しないと、for
が暗黙的に引数をループするという事実と、forループ変数のスコープが設定されていないという事実を使用します。
これはBash専用です。
echo "${@: -1}"
$ set quick brown fox jumps
$ echo ${*: -1:1} # last argument
jumps
$ echo ${*: -1} # or simply
jumps
$ echo ${*: -2:1} # next to last
fox
デフォルト値 として解釈されないようにスペースが必要です。
Bash 3.0以降の最も簡単な答えは
_last=${!#} # *indirect reference* to the $# variable
# or
_last=$BASH_ARGV # official built-in (but takes more typing :)
それでおしまい。
$ cat lastarg
#!/bin/bash
# echo the last arg given:
_last=${!#}
echo $_last
_last=$BASH_ARGV
echo $_last
for x; do
echo $x
done
出力は次のとおりです。
$ lastarg 1 2 3 4 "5 6 7"
5 6 7
5 6 7
1
2
3
4
5 6 7
次の長さと組み合わせたインデックスを使用します。
echo ${@:${#@}}
次はあなたのために働くでしょう。 @は引数の配列用です。 :はを意味します。 $#は引数の配列の長さです。したがって、結果は最後の要素になります。
${@:$#}
例:
function afunction{
echo ${@:$#}
}
afunction -d -o local 50
#Outputs 50
これは、最後の引数を前のすべての引数から分離するときに見つけました。答えのいくつかは最後の引数を取得しますが、他のすべての引数も必要な場合、それらはあまり役に立ちません。これははるかに優れています:
heads=${@:1:$(($# - 1))}
tail=${@:$#}
これはすべてのPOSIX互換シェルで機能します。
eval last=\${$#}
ソース: http://www.faqs.org/faqs/unix-faq/faq/part2/section-12.html
ここに私のソリューションがあります:
eval
コード:
ntharg() {
shift $1
printf '%s\n' "$1"
}
LAST_ARG=`ntharg $# "$@"`
Bash> = 3.0を使用している場合
echo ${BASH_ARGV[0]}
Ksh、zsh、およびbashの場合:
$ set -- The quick brown fox jumps over the lazy dog
$ echo "${@:~0}"
dog
そして「最後から次へ」の場合:
$ echo "${@:~1:1}"
lazy
ダッシュ(-n
など)で始まる引数の問題を回避するには、次を使用します。
$ printf '%s\n' "${@:~0}"
dog
sh
のスペースとグロブ文字を処理する正しい方法は次のとおりです。
$ set -- The quick brown fox jumps over the lazy dog "the * last argument"
$ eval echo "\"\${$#}\""
The last * argument
または、last
varを設定する場合:
$ eval last=\${$#}; echo "$last"
The last * argument
そして「最後から次へ」の場合:
$ eval echo "\"\${$(($#-1))}\""
dog
shift `expr $# - 1`
echo "$1"
これは、引数の数から1を引いた数だけ引数をシフトし、最初の(そして唯一の)残りの引数を返します。これが最後の引数になります。
私はbashでのみテストしましたが、shおよびkshでも動作するはずです。
非破壊的な方法でそれを行いたい場合、1つの方法はすべての引数を関数に渡し、最後の引数を返すことです。
#!/bin/bash
last() {
if [[ $# -ne 0 ]] ; then
shift $(expr $# - 1)
echo "$1"
#else
#do something when no arguments
fi
}
lastvar=$(last "$@")
echo $lastvar
echo "$@"
pax> ./qq.sh 1 2 3 a b
b
1 2 3 a b
実際にcareを使用しない場合、関数では必要ありませんが、他の引数を保持したくない状況を考えるのは困難ですそれらはすでに処理されています。その場合、私はそれらを順次処理するプロセス/シフト/プロセス/シフト/ ...メソッドを使用します。
ここではhave n'tがシーケンシャルメソッドに従っているため、それらを保持することを想定しています。このメソッドは、引数がない場合も処理し、「」を返します。コメントアウトされたelse
句を挿入することで、その動作を簡単に調整できます。
Tcshの場合:
set X = `echo $* | awk -F " " '{print $NF}'`
somecommand "$X"
これは、割り当てを除いて、ポータブルなソリューションになると確信しています。
bash
の場合、 このコメント は非常にエレガントであると示唆しています。
echo "${@:$#}"
以下は、現在の環境を変更せずにLAST
を最後の引数に設定します:
LAST=$({
shift $(($#-1))
echo $1
})
echo $LAST
他の引数が不要になり、シフトできる場合は、次のように簡略化できます。
shift $(($#-1))
echo $1
以下の移植性の理由から:
shift $(($#-1));
次のものに置き換えることができます。
shift `expr $# - 1`
$()
もバッククォートで置き換える:
LAST=`{
shift \`expr $# - 1\`
echo $1
}`
echo $LAST
eval
を使用したソリューション:
last=$(eval "echo \$$#")
echo $last
これは私のコピー機能の一部です:
eval echo $(echo '$'"$#")
スクリプトで使用するには、次の操作を行います。
a=$(eval echo $(echo '$'"$#"))
説明(最もネストされた最初):
$(echo '$'"$#")
は$[nr]
を返します。ここで[nr]
はパラメーターの数です。例えば。文字列$123
(展開されていない)。echo $123
は、評価時に123番目のパラメーターの値を返します。eval
は、$123
をパラメーターの値に展開するだけです。 last_arg
。これは文字列として解釈され、返されます。2015年半ばのBashで動作します。
上記の回答を読んだ後、PGM.cppでg ++を実行して実行可能なイメージPGMを生成するQ&Dシェルスクリプト(shとbashで動作するはずです)を作成しました。コマンドラインの最後の引数はファイル名(.cppはオプション)であり、他のすべての引数はオプションであると想定しています。
#!/bin/sh
if [ $# -lt 1 ]
then
echo "Usage: `basename $0` [opt] pgm runs g++ to compile pgm[.cpp] into pgm"
exit 2
fi
OPT=
PGM=
# PGM is the last argument, all others are considered options
for F; do OPT="$OPT $PGM"; PGM=$F; done
DIR=`dirname $PGM`
PGM=`basename $PGM .cpp`
# put -o first so it can be overridden by -o specified in OPT
set -x
g++ -o $DIR/$PGM $OPT $DIR/$PGM.cpp
echo $argv[$#argv]
回答が短すぎて投稿できないため、テキストを追加する必要があります。編集するテキストをさらに追加する必要があります。
@AgileZebraの答え(および@starfryのコメント)が最も便利であることがわかりましたが、heads
をスカラーに設定します。配列はおそらくより便利です。
heads=( "${@:1:$(($# - 1))}" )
tail=${@:${#@}}
以下のスクリプトを試して最後の引数を見つけてください
# cat arguments.sh
#!/bin/bash
if [ $# -eq 0 ]
then
echo "No Arguments supplied"
else
echo $* > .ags
sed -e 's/ /\n/g' .ags | tac | head -n1 > .ga
echo "Last Argument is: `cat .ga`"
fi
出力:
# ./arguments.sh
No Arguments supplied
# ./arguments.sh testing for the last argument value
Last Argument is: value
ありがとう。
#! /bin/sh
next=$1
while [ -n "${next}" ] ; do
last=$next
shift
next=$1
done
echo $last
これを行うには、はるかに簡潔な方法があります。 bashスクリプトの引数を配列に入れると、要素の処理がはるかに簡単になります。以下のスクリプトは、常にスクリプトに渡された最後の引数を出力します。
argArray=( "$@" ) # Add all script arguments to argArray
arrayLength=${#argArray[@]} # Get the length of the array
lastArg=$((arrayLength - 1)) # Arrays are zero based, so last arg is -1
echo ${argArray[$lastArg]}
サンプル出力
$ ./lastarg.sh 1 2 buckle my shoe
shoe
パラメーター展開を使用して(一致した先頭を削除):
args="$@"
last=${args##* }
最後まですべてを簡単に取得することもできます。
prelast=${args% *}