Bash脚本中将数组作为位置参数传入时丢失元素如何解决?
问题原因
你遇到的问题确实是数组作为位置参数传入的处理逻辑错误导致的:
当你在命令行执行sh BaseRecall.sh input ref "${Pickle[@]}"时,"${Pickle[@]}"会把数组的每一个元素展开为独立的位置参数,最终传入脚本的位置参数实际为:
- $1 = input
- $2 = ref
- $3 = dbSnp
- $4 = gold_standard_indels
你脚本中写的Pickle=$3只把第三个位置参数赋值给了变量,自然只能拿到第一个dbsnp值,后续的元素都存在$4、$5等位置参数中没有被捕获。
解决方法
修改脚本中Pickle变量的赋值逻辑,使用位置参数切片捕获从第3位开始的所有参数,组成数组即可:
#!/bin/bash #### Usage: < input > < ref > < (array of dbsnps) > input=$1 ref=$2 # 核心修改:从第3位开始取所有剩余位置参数赋值给Pickle数组 Pickle=("${@:3}") echo "${Pickle[@]}" ### Assign variables # 建议用数组存储命令参数,避免特殊字符、空格导致的异常 BaseReCall_args=( gatk BaseRecalibrator -I "$input" -R "$ref" -O recal_table ) dir=$(dirname "$input") log=${dir}/BaseReCall.out # 遍历dbsnp数组添加参数 for i in "${Pickle[@]}";do BaseReCall_args+=(--known-sites "$i") done # 打印命令 printf '%s\n' "${BaseReCall_args[*]}" # 实际执行命令直接调用即可:"${BaseReCall_args[@]}" >> "$log" 2>&1
修改后你原来的调用命令sh BaseRecall.sh input ref "${Pickle[@]}"就可以正常传入所有dbsnp值了。
补充注意事项
- 调用脚本时一定要给数组展开加双引号,也就是
"${Pickle[@]}",避免dbsnp路径包含空格时出现参数拆分错误 - 脚本内处理路径、参数时尽量给变量加双引号,减少特殊字符带来的异常
内容的提问来源于stack exchange,提问作者Ctat41
相关产品推荐
相关产品推荐

