我正在阅读几本关于bash脚本的书,并努力理解正确的引用和使用IFS
。也许有人可以帮我一个涉及带引号的文件名的小例子。从命令行执行此操作,即使它们包含空格,也可以正确打印文件名:
set - *
for i in "$@"; do echo $i; done
这不起作用,因为它在空格处断开:
set - `find . -name "*"`
for i in "$@"; do echo $i; done
也不是:
IFS=$'\0' set - `find . -name "*" -print0`
for i in "$@"; do echo $i; done
使用IFS=$'\n'
和的组合也不是-print
。为什么这些都失败了?
以下也失败了,但在这种情况下它出错(“bash:意外令牌'do'附近的语法错误”)。为什么?
IFS=$'\n' for i in `find . -name "*" -type f`; do echo $i; done
但这有效(注意“;”):
IFS=$'\n'; for i in `find . -name "*" -type f`; do echo $i; done
这会失败,因为文件名根本没有拆分(for
循环只有一次):
IFS=''; for i in `find . -name "*" -type f -print0`; do echo -e "$i\n"; done
那么,为什么第一个和第三个失败了?
最后,我认为在设定时IFS
,我是否''
相同$'\0'
?(我在之前的例子中尝试了两种方法。)如果是这样,为什么我显然需要$'\n'
而不仅仅是\n
?
* Bash是Ubuntu Gnome 16.04中的版本4.3.42(1)。
;
后的IFS=...
我不知道。这就像第二组3中的第二个案例。问题是,为什么需要这样做?我希望没有;
,变量的修改应该是临时的,在下面的命令中。我不希望它是永久性的。
IFS=$'\n'; set - `find`;
工作而不是IFS=$'\n' set - `find`;
。一种可能的解释是IFS=$'\n' set - `find`;
,find
被取代的,并与之前电流IFS记号化set
执行。
IFS=$'\n' set -
找。-name“*” - print``和for i in "$@"; do echo $i; done
。它肯定不起作用。