在 POSIX shell 中使用while 循环来处理文本通常被认为是不好的做法吗?
正如Stéphane Chazelas 所指出的,不使用 shell 循环的一些原因是概念、可靠性、易读性、性能和安全性。
这个答案解释了可靠性和易读性方面:
while IFS= read -r line <&3; do
printf '%s\n' "$line"
done 3< "$InputFile"
Run Code Online (Sandbox Code Playgroud)
为了性能,从文件或管道读取时,while
循环和读取非常慢,因为内置的read shell一次读取一个字符。
怎么样的概念和安全性方面?
我想我最好为此开始一个新的查询,因为我原来的查询已得到完全解答(谢谢!)。
我有两个文件,它们都是 postgresql 命令的输出。第一个 (/tmp/inventory.list) 是我原始查询使用 bash arrays 将表转换为 ini 文件的主题,为此我使用 @choroba 善意建议的 array 命令。鉴于我的第二个文件(/tmp/inventory2.list)的格式与第一个文件非常相似,我认为我可以调整数组脚本来类似地处理这个文件,但我显然把一些事情搞砸了。
我的输入文件 /tmp/inventory2.list 的格式为:
environment1 | hostname1.environment1.domain
environment1 | hostname2.environment1.domain
environment1 | hostname3.environment1.domain
environment2 | hostname4.environment2.domain
environment2 | hostname5.environment2.domain
environment3 | hostname6.environment3.domain
Run Code Online (Sandbox Code Playgroud)
必须以分组格式读入并写入另一个文件:
[environment1]
hostname1.environment1.domain
hostname2.environment1.domain
hostname3.environment1.domain
[environment2]
hostname4.environment2.domain
hostname5.environment2.domain
[environment3]
hostname6.environment3.domain
Run Code Online (Sandbox Code Playgroud)
环境分组之间必须有行空间,组名称必须按字母顺序显示,主机名必须在组内按字母顺序排序。每个环境组可能有多个主机名,但每个组只能显示一次。
让事情变得复杂的是,输入文件末尾有一个空行,我无法让我的 postgresql 查询省略它(-t 或 --tuples-only 删除通常写在末尾的行计数行,但不会' t 删除最后一个空行),因此需要将其删除并且不写入新的输出文件。
我尝试调整 @choroba 的数组命令来读取此文件并正确输出它,但是尽管它对于我的第一个文件完美地工作,但我的调整不起作用。我有:
1 #! /bin/bash
2
3 unset -v envs
4 unset -v hosts
5 declare -A envs
6 declare -A hosts …
Run Code Online (Sandbox Code Playgroud)