gpt4 book ai didi

带有循环和管道的 bash 函数

转载 作者:行者123 更新时间:2023-11-29 09:43:47 25 4
gpt4 key购买 nike

我有一个 bash 脚本,它将文件的内容通过管道传输到一系列用户定义的函数中,每个函数都对 stdin 执行 sed 操作,将输出发送到 stdout。

例如:

#!/bin/bash

MOD_config ()
{
sed 's/config/XYZ/g'
}

MOD_ABC ()
{
sed 's/ABC/WHOA!/g'
}

cat demo.txt \
| MOD_config \
| MOD_ABC

到目前为止一切顺利。一切都很好。

现在我想允许通过脚本的命令行指定额外的模式更改对。例如,我想允许用户运行以下任何一个:

demo.sh                           # changes per script (MOD_config and MOD_ABC)
demo.sh CDE 345 # change all 'CDE' to '345'
demo.sh CDE 345 AAAAA abababa # .. also changes 'AAAAA' to 'abababa'

所以我尝试将其添加到脚本中:

USER_MODS ()
{

if [ $# -lt 1]; then

#just echo stdin to stdout if no cmd line args exist
grep .

else

STARTING_ARGC=$#
I=1

while [ $I -lt $STARTING_ARGC ]; then

sed "s/$1/$2/g"

shift
shift
I=`expr $I + 2`

done

fi

}

cat demo.txt \
| MOD_config \
| MOD_ABC \
| USER_MODS

此方法仅在我没有命令行参数或只有两个时才有效。但是,在命令行上添加额外的参数没有任何效果。

不确定如何将 while 循环的一次迭代的标准输出发送到下一次迭代的标准输入。我认为这是我的问题的关键。

有解决办法吗?还是我应该采取完全不同的方法?

最佳答案

要有一个动态的管道列表,你需要一个递归的解决方案。有一个函数,它应用一组修改,然后用更少的两个参数调用自己。如果该函数没有参数,则只需调用 cat 将 stdin 原封不动地复制到 stdout。

mod() {
if (($# >= 2)); then
search=$1
replace=$2
shift 2

sed "s/$search/$replace/g" | mod "$@"
else
cat
fi
}

# Apply two base modifications, plus any additional user mods ("$@")
mod config XYZ ABC 'WHOA!' "$@"

关于带有循环和管道的 bash 函数,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/23410453/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com