Wak*_*nka 80 bash stdin pipe while-loop
Bash允许使用: cat <(echo "$FILECONTENT")
Bash还允许使用: while read i; do echo $i; done </etc/passwd
结合前两个可以使用: echo $FILECONTENT | while read i; do echo $i; done
最后一个问题是它创建了子shell,而在while循环结束后,变量i不再被访问.
我的问题是:
如何实现这样的目标:while read i; do echo $i; done <(echo "$FILECONTENT")或者换句话说:我怎样才能确定i循环中存活?
请注意我知道封闭while语句{}但这并不能解决问题(想象一下你想在函数中使用while循环并返回i变量)
Jon*_*ler 103
过程替换的正确表示法是:
while read i; do echo $i; done < <(echo "$FILECONTENT")
Run Code Online (Sandbox Code Playgroud)
i循环终止时,循环中分配的最后一个值可用.另一种选择是:
echo $FILECONTENT |
{
while read i; do echo $i; done
...do other things using $i here...
}
Run Code Online (Sandbox Code Playgroud)
大括号是一个I/O分组操作,本身不会创建子shell.在这种情况下,它们是管道的一部分,因此作为子shell运行,但它是因为而|不是{ ... }.你在这个问题中提到了这一点.AFAIK,你可以从这些函数内部返回.
Bash还提供shopt内置版本,其中许多选项之一是:
lastpipe如果设置,并且作业控制未激活,则shell将运行当前shell环境中未在后台执行的管道的最后一个命令.
因此,在脚本中使用这样的东西会使sum循环后修改可用:
FILECONTENT="12 Name
13 Number
14 Information"
shopt -s lastpipe # Comment this out to see the alternative behaviour
sum=0
echo "$FILECONTENT" |
while read number name; do ((sum+=$number)); done
echo $sum
Run Code Online (Sandbox Code Playgroud)
在命令行执行此操作通常会违反"作业控制未激活"(即,在命令行,作业控制处于活动状态).不使用脚本进行测试失败.
另外,正如Gareth Rees在他的回答中所指出的,你有时可以使用这里的字符串:
while read i; do echo $i; done <<< "$FILECONTENT"
Run Code Online (Sandbox Code Playgroud)
这不需要shopt; 您可以使用它保存进程.
Gar*_*ees 27
Jonathan Leffler解释了如何使用进程替换来执行您想要的操作,但另一种可能性是使用here字符串:
while read i; do echo "$i"; done <<<"$FILECONTENT"
Run Code Online (Sandbox Code Playgroud)
这节省了一个过程.
| 归档时间: |
|
| 查看次数: |
77014 次 |
| 最近记录: |