如何在带有 for 循环的 bash 脚本中使用标志?

Posted

技术标签:

【中文标题】如何在带有 for 循环的 bash 脚本中使用标志?【英文标题】:How to use flags in a bash script with for loop? 【发布时间】:2022-01-17 01:46:05 【问题描述】:

我最近在学习 bash,我想在这个 for 循环中使用标志来读取文件的头部和尾部。

for filename in "$1"

    do
    echo $filename
    head -n "$2" $filename | tail -n "$3"
  done

我想使用-f(而不是$1)、-h(而不是$2)、-t(而不是$3)等标志。

【问题讨论】:

for filename in "$1" 只会迭代一次。如果$1 是一个以空格分隔的文件列表,您可以通过删除引号并使用for filename in $1...来遍历它们,但不要这样做。 使用 getopts、getopt 之类的东西,或使用类似的东西自己动手:while $#; do if [ "$1" = "-f" ];then shift; f_arg="$1"; shift; elif ...pubs.opengroup.org/onlinepubs/9699919799/utilities/getopts.html 您应该澄清您的问题以显示您希望如何使用这些标志。我的理解是你想做的:./myscript -f file1 file2 ... fileN -h N1 -t N2 不是您的问题的答案,但您可以通过以下方式执行此循环:awk -v head=10 -v tail=2 'FNR==1print FILENAMEFNR<=head && FNR>head-tail' file1 ... fileN 或 (file*)。 使用像 -f 之类的标志(而不是 $1), .... 你到底是什么意思,为什么它特定于循环?请提供您想要实现的规范。 【参考方案1】:

与其试图将所有文件名塞进一个参数中,不如允许多个参数来指定路径。例如:

#!/bin/bash

# set defaults
h=10
t=5

while test -n "$1"; do
        filename=$1
        case $filename in
        -h) h=$2; shift; shift; continue;;
        -t) t=$2; shift; shift; continue;;
        esac

        if ! test "$h" -gt 0 || ! test "$t" -gt 0; then
                echo "Invalid entry" >&2;
                exit 1
        fi

        echo "$filename"
        # head -n "$h" $filename | tail -n "$t"
        d=$(( h - t ))
        sed -ne "$d,$hp" "$filename"
        shift
done

【讨论】:

以上是关于如何在带有 for 循环的 bash 脚本中使用标志?的主要内容,如果未能解决你的问题,请参考以下文章

如何使用for循环将文本文件中的一行字符串作为Bash中另一个脚本的单独变量传递[重复]

Bash for 具有多个条件的循环

使用for循环bash脚本逐行读取文件[重复]

使用带有两个变量的 for 循环

BASH:在 for 循环中使用 continue

用for循环编写删除文件的shell脚本