文件:
cat csvfile
apple,1
orange,2
banana,3
代码:
head -2 csvfile | while read line
do
f1=$(echo $line | cut -d ',' -f1)
f2=$(echo $line | cut -d ',' -f2)
echo "$f1 -> $f2"
done
while read line
do
f1=$(echo $line | cut -d ',' -f1)
f2=$(echo $line | cut -d ',' -f2)
echo "$f1 -> $f2"
done <<< $(head -2 csvfile)
输出:
apple -> 1
orange -> 2
apple -> 1 orange
答案1
问题是这样的:
$ echo "$(head -2 csvfile)"
apple,1
orange,2
$ echo $(head -2 csvfile)
apple,1 orange,2
当不加引号时,命令替换结果将受到单词拆分将所有空格序列(包括换行符)转换为单个空格。
现在只有一行需要迭代,echo $line | cut -d, -f2
输出1 orange
读忘记在 bash/POSIX shell 中引用变量的安全隐患
另一个潜在的问题将会出现后循环结束:考虑
head -2 csvfile | while read line
do
f1=$(echo $line | cut -d ',' -f1)
f2=$(echo $line | cut -d ',' -f2)
echo "$f1 -> $f2"
done
echo "$f1 -> $f2"
将输出->
但
while read line
do
f1=$(echo $line | cut -d ',' -f1)
f2=$(echo $line | cut -d ',' -f2)
echo "$f1 -> $f2"
done < <(head -2 csvfile) # <<< a Process Substitution
echo "$f1 -> $f2"
orange -> 2
将按预期输出。
Bash 管道在单独的子 shell 中执行每个命令。如果while read
管道中最后一个命令,则其变量将在该子 shell 退出时消失。
如果你需要变量持久化,就不要管道输入到 while 循环中,重定向输入。
进一步阅读: