Bash 使用getopts将文件名存储为参数
我正试图学习使用bash中的getopts()功能来解析我的参数,但我的程序要求,除了标准的-a-b-c类型参数外,我还需要处理任意数量的文件,我找不到任何关于如何让getopts识别它们而不是将它们作为无效参数抛出的信息。下面是一个例子:Bash 使用getopts将文件名存储为参数,bash,for-loop,Bash,For Loop,我正试图学习使用bash中的getopts()功能来解析我的参数,但我的程序要求,除了标准的-a-b-c类型参数外,我还需要处理任意数量的文件,我找不到任何关于如何让getopts识别它们而不是将它们作为无效参数抛出的信息。下面是一个例子: 当getopts“a:b:c:d”标志时 做 echo do:“$flag”$optand$OPTARG 如果[“$flag”=a];然后 first=“$OPTARG” echo找到参数:$first fi 。。。其他if语句也是如此。如果我的程序只需要
当getopts“a:b:c:d”标志时
做
echo do:“$flag”$optand$OPTARG
如果[“$flag”=a];然后
first=“$OPTARG”
echo找到参数:$first
fi
。。。其他if语句也是如此。如果我的程序只需要一个像:program-a-c这样的命令,那么这非常有效,但是我需要接受像:program-a file.sh-c otherfile.sh这样的命令
有人能给我举一个这样的例子吗?下面是我的一个shell脚本片段,它使用并或多或少地按照您的意愿执行:
arg0=$(basename $0 .sh)
usage()
{
echo "Usage: $arg0 [-qvF] [-s suffix] -j jdcfile file.msd" 1>&2
exit 1
}
error()
{
echo "$arg0: $*" 1>&2
exit 1
}
Fflag=
suffix=
jdcfile=
qflag=
vflag=no
while getopts Fj:qs:v opt
do
case "$opt" in
(F) Fflag="-F";;
(j) jdcfile="$OPTARG";;
(q) qflag="-q";;
(s) suffix="$OPTARG";;
(v) vflag=yes;;
(*) usage;;
esac
done
shift $(($OPTIND - 1))
case $# in
(1) : OK;;
(*) usage;;
esac
if [ -z "$jdcfile" ]
then error "you did not specify which jdcfile to use (-j option)"
fi
msd_file=$1
我想,你缺少的部分是shift
。以及getopts
处理循环之后命令行上剩余参数的后续处理
在这个特定程序的末尾,在“$@”
中正好有一个文件名需要处理。对于这个特定的程序,没有文件或列出多个文件是一个错误。您可以删除最后的案例
,或根据需要修改它。此代码还强制执行-jdcfile
“选项”;它是一个强制参数,如用法消息所示
移位后更典型的模式是:
for file in "$@"
do
...processing of $file...
done
这只会让您处理零文件名的情况
error
和usage
函数也是有用的大纲/原型。如注释中所述,如果您愿意,您可以在选项字符串上使用前导的:
,来负责错误处理。我选择不这样做,但我忘了这是我做出的决定。基于我上面的评论-你不想为此使用getopts
。更简单的方法将起作用:
#!/bin/bash
args=()
for arg in "$@"
do
case "$arg" in
"-a" )
echo "We have an '-a'!"
;;
"-b" )
echo "We have a '-b'!"
;;
* )
args+=($arg)
esac
done
echo And we have these arguments: ${args[*]}
要查看其运行,请执行以下操作:
$ ./program one -a two three -b four
We have an '-a'!
We have a '-b'!
And we have these arguments: one two three four
我不明白。你已经在做了。如果调用程序-a file.sh
,则首先会得到分配给file.sh
的变量。请参阅,这就是问题所在。文件名在此脚本中是独立参数,而不是其他参数的参数。一个文件应该能够像“script.sh-a4filename.sh”一样输入,其中“filename.sh”将被检测为它自己的参数。对不起,我说得不清楚。使用getopts
无法实现这一点。它将停止在第一件事,是不是在它的规格。这就是为什么几乎所有unix实用程序都让您最后编写非选项参数的原因。对于您的用例,我只使用参数上的普通循环-getopts
对于您想要的内容来说有点太聪明了。通常,您希望参数的第一个字符getopts
为冒号,以便您可以自己处理错误。您将为\?)echo“未知选项-$OPTARG”添加一个案例
代码>,:)echo“缺少-$OPTARG的选项参数”代码>和*)回显“未限制选项-$OPTARG.”代码>。顺便说一下,在usage()
中的回答中,您使用了$arg0
,但在error()
中,您使用了$0
。感谢您提供我脚本中的错误报告。这是一个普遍存在的问题;我不得不用这一个修复套件中的6个脚本,另一个修复了类似但稍微复杂的问题。