bash脚本传递参数的方法

1、位置参数:如 michael michelle

创建脚本 test.sh

#!/bin/bash
echo "第一个参数是 $1"
echo "第二个参数是 $2"

调用脚本

./test.sh michael michelle
----------------------------------------------执行打印结果
第一个参数是 michael
第二个参数是 michelle

2、特殊变量参数:如 $0 $# $@ $?

创建脚本 test.sh

#!/bin/bash
echo "The script name is $0"
echo "The number of arguments is $#"
echo "The arguments are $@"
echo "The return value of the last command is $?"

相对路径调用脚本


./test.sh michael michelle
----------------------------------------------执行打印结果
The script name is ./test.sh
The number of arguments is 2
The arguments are michael michelle
The return value of the last command is 0

绝对路径调用脚本

/root/bbb/test.sh aaa bbb ccc
----------------------------------------------执行打印结果
The script name is /root/bbb/test.sh
The number of arguments is 3
The arguments are aaa bbb ccc
The return value of the last command is 0

3、环境变量

在shell脚本中,可以使用$VAR的形式来访问环境变量。在脚本里获取环境变量,可对执行环境进行检验。

#!/bin/bash
echo "HOME变量的值是=$HOME"
echo "LANG变量的值是=$LANG"
echo "PWD变量的值是=$PWD"

调用脚本

./test.sh
----------------------------------------------执行打印结果
HOME变量的值是=/root
LANG变量的值是=en_US.UTF-8
PWD变量的值是=/root/bbb

4、命名参数:getopts

getopts是 bash 自带的命令行参数处理工具,它的语法比较简单,只支持处理单个字母选项,例如-a-b等。getopts只能处理短选项,也就是只能使用一个字母来表示选项,如果要处理长选项,需要编写更多的代码。另外,getopts处理命令行参数时会把选项和参数分别处理,不能处理连续的选项,例如-abc。

#!/bin/bash
HOST=192.168.168.168
PORT=8848
echo "HOST=${HOST} PORT=${PORT}"

while getopts ":h:p:" opt
do
    case $opt in
        h)
            HOST=$OPTARG;;
        p)
            PORT=$OPTARG;;
        ?)
            echo "Unknown parameter"
            exit 1;;
    esac
done

echo "HOST=${HOST} PORT=${PORT}"

调用脚本

./test.sh
----------------------------------------------执行打印结果
HOST=192.168.168.168 PORT=8848
HOST=192.168.168.168 PORT=8848

调用脚本

./test.sh -h 10.10.10.10 -p 8848
----------------------------------------------执行打印结果
HOST=192.168.168.168 PORT=8848
HOST=10.10.10.10 PORT=8848

调用脚本

./test.sh -h 10.10.10.10 -p 8848 -u michael
----------------------------------------------执行打印结果
HOST=192.168.168.168 PORT=8848
Unknown parameter

5、命名参数:getopt

getopt是GNU工具集中的一个命令行参数处理工具,它支持更多的选项和语法,可以处理短选项长选项,还可以处理连续的选项getopt的语法比getopts更加复杂,需要指定一个选项字符串,包含了所有支持的选项和参数。getopt将解析后的选项和参数保存在一个数组中,需要在代码中处理这个数组。

getopt命令有以下几个参数:
-o:指定单字符选项。选项之间无需分隔符。
--long:指定长选项。长选项之间使用逗号分隔。
:::选项后添加冒号说明当前选项需要参数值。
--:分割选项和参数。
“$@”:表示将所有命令行参数作为一个字符串传递给getopt命令。

options=$(getopt -o n:a:g:p --long name:,age:,gender:,print -- "$@")会解析命令行选项和参数,并将转换后的选项和参数存储在变量options中。这个变量通常会传递给一个eval命令进行处理,例如:
eval set -- "$options"

# 测试脚本
#!/bin/bash
# 解析命令行参数
options=$(getopt -o n:a:g:p --long name:,age:,gender:,print -- "$@")
eval set -- "$options"
 
# 提取选项和参数
while true; do
  case $1 in 
  	-a | --age) shift; age=$1 ; shift ;;
    -n | --name) shift; name=$1 ; shift ;;
    -g | --gender) shift; gender=$1 ; shift ;;
    -p | --print) print=true; shift ;;
    --) shift ; break ;;
    *) echo "Invalid option: $1" exit 1 ;;
  esac
done
 
# 检查变量
if [ -z "$age" ]; then
    echo "Error: age is required"
    exit 1
fi
if [ -z "$name" ]; then
    echo "Error: name is required"
    exit 1
fi
if [ -z "$gender" ]; then
    echo "Error: gender is required"
    exit 1
fi
 
# 判断开关选项
if [ "$print" = true ]; then
    echo "NameVal: $name; AgeVal: $age; GenderVal: $gender";
fi

# 脚本调用(长选项)
./script.sh --name Kite --age 18 --gender f -p
NameVal: Kite; AgeVal: 18; GenderVal: f
# 脚本调用(单字符选项)
./script.sh -n Kite -a 18 -g f -p
NameVal: Kite; AgeVal: 18; GenderVal: f

待整理

#!/bin/bash
#testPa.sh -uxxx -pxxx -txxx -dyyyyyMMdd

#set接受参数
v_user=""
v_pwd=""
v_table=""
v_date=$(date -d"-1 days" +"%Y%m%d")

#接收可选参数
while getopts :u:p:t:d: opt
do
  case "$opt" in
  u) v_user=$OPTARG;; 
  p) v_pwd=$OPTARG;;
  t) v_table=$OPTARG;;
  d) v_date=$OPTARG;;
  *) echo "Unknown option: $opt" ;;
  esac
done

echo "v_user=${v_user} v_pwd=${v_pwd} v_table=${v_table} v_date=${v_date}"

shift $[ $OPTIND - 1 ]

#进入脚本目录
#cd $(dirname $0)
echo $(dirname $0)

#获取根目录
#BASEHOME=$(dirname $PWD)
echo $(dirname $PWD)
[root@VM_0_11_centos test]# pwd
/root/test
[root@VM_0_11_centos test]# bash testPa.sh 
v_user= v_pwd= v_table= v_date=20191120
.
/root
[root@VM_0_11_centos test]# 

#!/bin/bash
echo $*
while getopts ":a:bc:" opt
do
	case $opt in
		a) echo $OPTARG $OPTIND;;
		b) echo "b $OPTIND";;
		c) echo "c $OPTIND";;
		?) echo "error";
		   exit 1;;
	esac
done
echo $OPTIND
shift $(( $OPTIND-1 ))
echo $0
echo $*
[root@VM_0_11_centos test]# /root/test/test2.sh -aaaa -bbbb -cccc
-aaaa -bbbb -cccc
aaa 2
b 2
b 2
b 2
b 3
c 4
4
/root/test/test2.sh
结果这里有一个空行

custom1.list文件内容

[N01] michael 1001
[N02] bob 1002
[N02] michelle 1003

bash读取配置文件

#!/bin/bash

while group name id
do
	echo "${group} === ${name} === ${id}"
done < /root/custom1.list
[N01] === michael === 1001
[N02] === bob === 1002
[N02] === michelle === 1003

getopts的使用
语法格式:
getopts [option[:]] [DESCPRITION] VARIABLE
option :表示为某个脚本可以使用的选项
":" :如果某个选项(option)后面出现了冒号(":"),则表示这个选项后面可以接参数(即一段描述信息DESCPRITION)
VARIABLE :表示将某个选项保存在变量VARIABLE中
 
getopts :是linux系统中的一个内置变量,一般用在循环中。每当执行循环是,getopts都会检查下一个命令选项,如果这些选项出现在option中,则表示是合法选项,否则不是合法选项。并将这些合法选项保存在VARIABLE这个变量中。
getopts :还包含两个内置变量,及OPTARG和OPTIND
OPTARG :就是将选项后面的参数(或者描述信息DESCPRITION)保存在这个变量当中。
OPTIND :这个表示命令行的下一个选项或参数的索引(文件名不算选项或参数)

---------------------------------------------------
#!/bin/bash
while getopts ':b:d:' OPT &> /dev/null;do
	case $OPT in
		b)
		echo "The options is b"
		echo $OPTARG ;;
		d)
		echo "The options is d"
		echo $OPTARG ;;
		*)
		echo "Wrong Options"
		exit 7 ;;
	esac
	# echo $OPT
	# echo $OPTARG
done
echo $OPTIND
shift $[$OPTIND-1]
echo $1

----------------------------------------------------------
###执行脚本时,显示的结果如下###
[root@localhost scriptTEAM]# ./test -d 'nice' fixnale
The options is d  
nice
3
fixnale
###显示信息说明如下###
当输入-d时,$OPT=d,$OPTARG='nice',因此就会显示d)...这一部分的信息。
由于这里有一个选项(-d)和一个参数('nice'),$OPTIND指向命令行中下一个选项或参数的索引位置,因此这里即为3。
shift $[$OPTIND-1]表示将文件名前面的选项和参数踢掉

=============================================================================================================

[root@localhost ~]# cat getopts.sh
#!/bin/bash
echo $*
while getopts ":a:bc:" opt
do
    case $opt in
        a) echo $OPTARG $OPTIND;;
        b) echo "b $OPTIND";;
        c) echo "c $OPTIND";;
        ?) echo "error" 
		   exit 1;;
    esac
done
echo $OPTIND
shift $(( $OPTIND-1 ))
echo $0
echo $*
-----------------------------------------------------
[root@localhost ~]# sh getopts.sh -a 11 -b -c 6
-a 11 -b -c 6
11 3
b 4
c 6
6
getopts.sh
--------------------------------------------------


为什么会得到上面的结果呢?

while getopts ":a:bc:" opt #第一个冒号表示忽略错误;字符后面的冒号表示该选项必须有自己的参数。

$OPTARG 存储相应选项的参数,如上例中的11、6;

$OPTIND 总是存储原始$*中下一个要处理的选项(不是参数,而是选项,此处指的是a,b,c这三个选项,而不是那些数字,当然数字也是会占有位置的)位置。

optind初值为1,遇到"x",选项不带参数,optind+=1;遇到"x:",带参数的选项,optarg=argv[optind+1],optind+=2;遇到"x::",可选参数,属于#1和#2之一(转载过来的,这句我也看不懂)

第一行输出echo $*
第二行,optind初值为1,选项-a的参数为11,下一个要处理的选项-b位置为3,所以输出:11 3;
第三行,然后-b要处理的下一个选项-c位置为4,所以输出:b 4;
第四行,再者-c有参数,所以下一个要处理的位置+2,所以输出:c 6;


------------------------------------------------------------------
[root@localhost ~]# sh getopts.sh -a 11 -b -b 9 -c 6
-a 11 -b -b 5 -c 6
11 3
b 4
b 5
5
getopts.sh
9 -c 6
------------------------------------------------------------
起初我看到以上的输出结果百思不得其解,后面多试几次选项及参数后,大概猜了一下。
第一行输出echo $*
第二行,optind初值为1,下一个要处理的选项-b位置为3,所以输出11 3;
第三行,下一个要处理的选项-b位置为4,所以输出b 4;
第四行,下一个要处理的选项-b位置为5,所以输出b 5;
程序现在遇到9,不属于getopts,所以停止循环while,下面几行就不解释了。
getopt 与 getopts 都是 Bash 中用来获取与分析命令行参数的工具,常用在 Shell 脚本中被用来分析脚本参数。

两者的比较
(1)getopts 是 Shell 内建命令,getopt 是一个独立外部工具
(2)getopts 使用语法简单,getopt 使用语法较复杂
(3)getopts 不支持长参数(如:--option ),getopt 支持
(4)getopts 不会重排所有参数的顺序,getopt 会重排参数顺序(这里的区别下面会说明)
(5)getopts 出现的目的是为了代替 getopt 较快捷的执行参数分析工作



10 通义千问的回答

getoptgetopts 都是 Bash 脚本中用于解析命令行参数的工具,但它们之间存在一些关键的区别。

getopt

getopt 是一个 Unix/Linux 命令行实用程序,用于解析命令行选项。它能处理带短选项(如 -f)和长选项(如 --file)的命令行参数,并能处理带有参数的选项(如 -f filename)。

getopt 的主要优点是它可以处理选项和参数的复杂组合,而且它的输出格式可以被解析,以供脚本进一步处理。但是,getopt 的语法和使用相对复杂。

使用示例
#!/bin/bash

ARGS=$(getopt -o f:o: --long file:,output: -- "$@")
if [ $? != 0 ]; then
  echo "Terminating..." >&2
  exit 1
fi

eval set -- "$ARGS"

while true; do
  case "$1" in
    -f | --file ) FILE="$2"; shift 2 ;;
    -o | --output ) OUTPUT="$2"; shift 2 ;;
    -- ) shift; break ;;
    * ) break ;;
  esac
done

echo "File: $FILE"
echo "Output: $OUTPUT"

getopts

getopts 是 Bash 内置的一个函数,用于解析简单的命令行选项。它只能处理短选项,不能直接处理长选项,也不能很好地处理选项和参数混合的情况。但是,getopts 的语法简单直观,适合处理简单的命令行参数。

使用示例
#!/bin/bash

while getopts ":f:o:" opt; do
  case $opt in
    f )
      FILE=$OPTARG
      ;;
    o )
      OUTPUT=$OPTARG
      ;;
    \? )
      echo "Invalid option: -$OPTARG" >&2
      ;;
    : )
      echo "Option -$OPTARG requires an argument." >&2
      ;;
  esac
done

shift $((OPTIND -1))

echo "File: $FILE"
echo "Output: $OUTPUT"

总结

  • getopt 更适合处理复杂的命令行选项和参数,特别是当需要处理长选项和带有参数的选项时。
  • getopts 更适合处理简单的命令行选项,语法更简单,易于理解和编写。

选择哪个工具取决于你的脚本需要处理的命令行参数的复杂程度。

  • 2
    点赞
  • 3
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值