![如何在 Bash 脚本中的不同行上为每个标志添加注释?](https://linux22.com/image/1376939/%E5%A6%82%E4%BD%95%E5%9C%A8%20Bash%20%E8%84%9A%E6%9C%AC%E4%B8%AD%E7%9A%84%E4%B8%8D%E5%90%8C%E8%A1%8C%E4%B8%8A%E4%B8%BA%E6%AF%8F%E4%B8%AA%E6%A0%87%E5%BF%97%E6%B7%BB%E5%8A%A0%E6%B3%A8%E9%87%8A%EF%BC%9F.png)
我想要编写尽可能自记录的 bash 脚本。
我有一个想法,当我执行带有大量标志的软件时,我想将命令分成多行,并在每行末尾添加一条注释,说明该标志的作用(来自手册页的信息),如下所示:
bwa aln \
-n $n \ # -n max #diff (integer) or missing prob under 0.02 err rate (float) [0.04]
-o $o \ # -o maximum number or fraction of gap opens [1]
-e $e \ # -e maximum number of gap extensions, -1 for disabling long gaps [-1]
-i $i \ # -i do not put an indel within integer bp towards the ends [5]
-d $d \ # -d maximum occurrences for extending a long deletion [10]
-l $l \ # -l seed length [32]
-k $k \ # -k maximum differences in the seed [2]
-m $m \ # -m maximum entries in the queue [2000000]
-t $t \ # -t number of threads [1]
-M $M \ # -M mismatch penalty [3]
-O $O \ # -O gap open penalty [11]
-E $E \ # -E gap extension penalty [4]
-R $R \ # -R stop searching when there are >integer equally best hits [30]
-q $q \ # -q quality threshold for read trimming down to 35bp [0]
-f $f \ # -f file to write output to instead of stdout
-B $B \ # -B length of barcode
-L $L \ # -L log-scaled gap penalty for long deletions
-N $N \ # -N non-iterative mode: search for all n-difference hits (slooow)
-I $I \ # -I the input is in the Illumina 1.3+ FASTQ-like format
-b $b \ # -b the input read file is in the BAM format
-0 $0 \ # -0 use single-end reads only (effective with -b)
-1 $1 \ # -1 use the 1st read in a pair (effective with -b)
-2 $2 \ # -2 use the 2nd read in a pair (effective with -b)
-Y $Y \ # -Y filter Casava-filtered sequences
-prefix $prefix \ # -prefix Prefix
-inputfile $inputfile \ # -inputfile Input file (FastQ format)
问题是我不能在 \ 字符后面添加任何内容(它告诉 bash 命令在下一行继续),也不能在行尾添加“\”,因为这样它会被视为注释的一部分。
有人知道这样做的方法,或者类似的事情吗?
答案1
您可以在斜杠前评估注释,只需为不会影响脚本的注释生成空字符串:
bwa aln \
-n $n `# -n max #diff (integer) or missing prob under 0.02 err rate (float) [0.04]` \
-o $o `# -o maximum number or fraction of gap opens [1]` \
....
答案2
我建议使用多行来注释命令前的代码。比如
# this command uses multiple parameters
# it requires 4 parameters and none are optional with no defaults
# parameters used :
# -q name of the file
# -b size to truncate
# -n new location
# -r recursive
答案3
一个选择是分部分构建你的命令,这样你就不必担心行的延续:
cmd='date' # run the date program
cmd=${cmd}' -d 20130905' # for this date
cmd=${cmd}' +%s' # with output in this format
echo $cmd # review the command
eval $cmd # run the command
答案4
对我来说,类似这样的方法已经足够好了。解决方案专注于通过连接构建字符串。(比较发布版本与调试版本)
#############################################################################
#### GRPC ########################################################## GRPC ###
#############################################################################
# GRPC - depends on protobuf (above)
#
# gRPC_BUILD_CODEGEN=ON - needed to build grpc_cpp_plugin
# ABSL_ENABLE_INSTALL=ON - needed to install Abseil
#
TYPE=RelWithDebInfo
INSTALL=${BUILD_DIR}/install-${TYPE}
BUILD=build-grpc-${TYPE}
echo "Building: $BUILD <-------------------------------------------------------"
(cd ${BUILD_DIR} && rm -rf $BUILD && mkdir -p $BUILD) || exit 1
(cd ${BUILD_DIR}/$BUILD && cmake ${DIR}/../grpc \
-DgRPC_BUILD_TESTS=OFF \
-DgRPC_BUILD_CODEGEN=ON \
-DgRPC_BUILD_CSHARP_EXT=OFF \
-DgRPC_INSTALL=ON \
-DgRPC_PROTOBUF_PROVIDER=package \
-DgRPC_SSL_PROVIDER=package \
-DgRPC_ZLIB_PROVIDER=package \
-DgRPC_BUILD_GRPC_CPP_PLUGIN=ON \
-DgRPC_BUILD_GRPC_PYTHON_PLUGIN=ON \
-DgRPC_BUILD_GRPC_CSHARP_PLUGIN=OFF \
-DgRPC_BUILD_GRPC_NODE_PLUGIN=OFF \
-DgRPC_BUILD_GRPC_OBJECTIVE_C_PLUGIN=OFF \
-DgRPC_BUILD_GRPC_PHP_PLUGIN=OFF \
-DgRPC_BUILD_GRPC_PHP_PLUGIN=OFF \
-DgRPC_BUILD_GRPC_RUBY_PLUGIN=OFF \
-DABSL_ENABLE_INSTALL=ON \
-DBUILD_SHARED_LIBS=OFF \
-DCMAKE_BUILD_TYPE=${TYPE} \
-DCMAKE_CXX_COMPILER=clang++ -DCMAKE_C_COMPILER=clang \
-DCMAKE_INSTALL_PREFIX=${INSTALL}) || exit 1
(cd ${BUILD_DIR}/$BUILD && cmake --build . --target install -j $THREADS) || exit 1
(cd ${BUILD_DIR} && rm -rf $BUILD) # Cleanup
#############################################################################
#############################################################################
TYPE=Debug
INSTALL=${BUILD_DIR}/install-${TYPE}
BUILD=build-grpc-${TYPE}
echo "Building: $BUILD <-------------------------------------------------------"
(cd ${BUILD_DIR} && rm -rf $BUILD && mkdir -p $BUILD) || exit 1
GRPC_BUILD_FLAGS=" -DgRPC_BUILD_TESTS=OFF"
GRPC_BUILD_FLAGS="${GRPC_BUILD_FLAGS} -DgRPC_BUILD_CODEGEN=ON"
GRPC_BUILD_FLAGS="${GRPC_BUILD_FLAGS} -DgRPC_BUILD_CSHARP_EXT=OFF"
GRPC_BUILD_FLAGS="${GRPC_BUILD_FLAGS} -DgRPC_BUILD_CSHARP_EXT=OFF"
GRPC_BUILD_FLAGS="${GRPC_BUILD_FLAGS} -DgRPC_INSTALL=ON"
GRPC_BUILD_FLAGS="${GRPC_BUILD_FLAGS} -DABSL_ENABLE_INSTALL=ON" # needed to install Abseil
GRPC_BUILD_FLAGS="${GRPC_BUILD_FLAGS} -DgRPC_PROTOBUF_PROVIDER=package"
GRPC_BUILD_FLAGS="${GRPC_BUILD_FLAGS} -DgRPC_SSL_PROVIDER=package"
GRPC_BUILD_FLAGS="${GRPC_BUILD_FLAGS} -DgRPC_ZLIB_PROVIDER=package"
GRPC_BUILD_FLAGS="${GRPC_BUILD_FLAGS} -DgRPC_BUILD_GRPC_CPP_PLUGIN=ON"
GRPC_BUILD_FLAGS="${GRPC_BUILD_FLAGS} -DgRPC_BUILD_GRPC_PYTHON_PLUGIN=ON"
GRPC_BUILD_FLAGS="${GRPC_BUILD_FLAGS} -DgRPC_BUILD_GRPC_CSHARP_PLUGIN=OFF"
GRPC_BUILD_FLAGS="${GRPC_BUILD_FLAGS} -DgRPC_BUILD_GRPC_NODE_PLUGIN=OFF"
GRPC_BUILD_FLAGS="${GRPC_BUILD_FLAGS} -DgRPC_BUILD_GRPC_OBJECTIVE_C_PLUGIN=OFF"
GRPC_BUILD_FLAGS="${GRPC_BUILD_FLAGS} -DgRPC_BUILD_GRPC_PHP_PLUGIN=OFF"
GRPC_BUILD_FLAGS="${GRPC_BUILD_FLAGS} -DgRPC_BUILD_GRPC_PHP_PLUGIN=OFF"
GRPC_BUILD_FLAGS="${GRPC_BUILD_FLAGS} -DgRPC_BUILD_GRPC_RUBY_PLUGIN=OFF"
GRPC_BUILD_FLAGS="${GRPC_BUILD_FLAGS} -DBUILD_SHARED_LIBS=ON"
GRPC_BUILD_FLAGS="${GRPC_BUILD_FLAGS} -DCMAKE_BUILD_TYPE=${TYPE}"
(cd ${BUILD_DIR}/$BUILD && cmake ${DIR}/../grpc \
${GRPC_BUILD_FLAGS} \
-DCMAKE_CXX_COMPILER=clang++ -DCMAKE_C_COMPILER=clang \
-DCMAKE_INSTALL_PREFIX=${INSTALL}) || exit 1
(cd ${BUILD_DIR}/$BUILD && cmake --build . --target install -j $THREADS) || exit 1
(cd ${BUILD_DIR} && rm -rf $BUILD) # Cleanup
#############################################################################