使用命令的输出作为循环中同一命令的输入

使用命令的输出作为循环中同一命令的输入

所以我试图找到一个 bash/shell 脚本的模板,它本质上运行一个命令,让我们使用输入“X”将其称为“command1”,然后在其本身上使用 command1 的输出......但在一个循环中。

这是一个现实世界的例子:

echo "hello" | cut -c2-

这将删除输入字符串开头的第一个字符并输出:

ello

现在,上面只是一个例子来说明上面提到的模板。按照这个例子,我该如何使用命令1输出:

echo "hello" | cut -c2-

但作为输入,在循环中,要么无限循环,要么直到只剩下一个字节/字符。

这样我就不需要复制/粘贴输出并将其替换为旧输入:

echo "ello" | cut -c2-

或者需要使用多个管道,这会太慢/效率低下。

更简单的解释

使用手动操作,这将替换我(用户)复制粘贴我作为示例给出的命令的输出(或我之前描述的伪代码),并将其用作同一命令的输入,重复相同的操作,直到剩余“一个”字节或字符。

答案1

如果我理解正确的话,您正在寻找这样的东西:

$ var=hello
$ while [ -n "$var" ]; do 
    printf -- "Var is now '%s'\n" "$var"
    var=$(printf -- '%s\n' "$var" | cut -c2-); 
done
Var is now 'hello'
Var is now 'ello'
Var is now 'llo'
Var is now 'lo'
Var is now 'o'

答案2

这确实有效在Linux上:

echo hello | tee /dev/fd/0
hello
hello
hello
...

echo hello | gawk '!length{exit(0)} {print; print substr($0,2) >"/dev/fd/3"; fflush()}' 3>/dev/fd/0
hello
ello
llo
lo
o

这利用了这样一个事实:在 Linux 上,所有管道实际上都是命名管道(即它们可以通过路径打开)。使用常规命名管道,它也可以在其他 Unix 系统上工作 - 请参阅此回答在 Stackoverflow 上。

答案3

你可以用递归来做到这一点:

command1() {
  local var
  IFS= read -r var
  if [[ $var ]]; then
    printf '%s\n' "$var"
    cut -c2- <<< "$var" | "${FUNCNAME[0]}"
  fi
}

然后:

$ echo hello | command1
hello
ello
llo
lo
o

答案4

这似乎有效:

foo() { [[ ! "${#1}" -eq 1 ]] && printf "%s" "$1" | cut -c2-; }

bar="hello"

while [[ ! -z $(foo "$bar") ]]; do bar=$(foo "$bar"); printf "%s\n" "$bar"; done

ello
llo
lo
o

相关内容