For loop 如何避免在zsh for循环中使用空格作为分隔符?

For loop 如何避免在zsh for循环中使用空格作为分隔符?,for-loop,sh,zsh,separator,For Loop,Sh,Zsh,Separator,我正在尝试制作一个小脚本来转换音乐库中的一些文件 但如果我这样做: #!/usr/bin/zsh for x in $(find -name "*.m4a"); do echo $x; done 在包含以下内容的文件夹中进行口译时: foo\ bar.m4a 它将返回: foo bar.m4a 如何防止for循环将空格字符解释为分隔符 我可以将

我正在尝试制作一个小脚本来转换音乐库中的一些文件

但如果我这样做:

#!/usr/bin/zsh                                                                     

for x in $(find -name "*.m4a");
do
    echo $x;
done
在包含以下内容的文件夹中进行口译时:

foo\ bar.m4a
它将返回:

foo
bar.m4a
如何防止for循环将空格字符解释为分隔符

我可以将
$(find-name“*.m4a”)
替换为
$(find-name“*.m4a”| sed“s//g”)
,然后在循环中以另一种方式使用
sed
,但如果文件名/路径已经包含下划线(或者我可以使用其他字符代替下划线),该怎么办

有什么想法吗?

我发现了

正如这里所建议的:

我可以将IFS(内部字段分隔符)设置为“\n”

所以这是可行的:

#!/usr/bin/zsh                                                                                          

IFS=$'\n'
for x in $(find -name "*.m4a");
do
    echo $x;
done

我希望这能帮助别人

在此处使用
zsh
的全球化工具,而不是
find

for x in **/*.m4a; do
    echo "$x"
done

zsh
的默认设置下,在循环体中引用
$x
是可选的,但这样做也不是一个坏主意。

您可以通过双引号防止命令替换的分词:

#!/usr/bin/zsh                                                                     

for x in "$(find -name "*.m4a")"
do
    echo "$x"
done
请注意,命令替换中的双引号与命令替换外的双引号并不冲突(我以前从未注意到这一点)。如果您觉得单引号更具可读性,则可以像在
“$(find-name'*.m4a')”
中一样轻松地使用单引号。我通常在
find
primary中使用单引号

出于同样的原因,在循环体内部引用也很重要。它将确保
x
的值作为单个参数传递

但这绝对是一个混合的,弗兰肯斯坦式的解决方案。您最好使用或使用
find
,如下所示:

find . -name '*.mp3' -exec echo {} \;

但这种形式是有限的。您可以添加额外的
-exec
主键,这些主键将像shell命令一样执行,由
&&
分隔,但您不能从一个
-exec
管道传输到另一个
-exec
,也不能与shell交互(例如,通过分配或扩展参数).

人们会跳过您在
find
的输出上使用for循环的案例。。如果可以的话,可以在使用find的internal-exec特性时执行它。该功能在find实现中是可移植的,并有助于避免您在解析
循环和文件名空白时遇到的问题。这就是我所说的。可以设置IFS变量,以便对shell用于标记化的分隔符进行细粒度控制。通常,IFS最简单的用法是只将其设置为与下面完全相同的值:IFS=这不适用于名称中包含换行符(罕见但合法)的文件。@chepner newlines in filenames?我要走了old@Jonathan我不确定他们是否曾经不合法;人们只是为了使代码更容易编写而避开它们。很好的一个!我没想过。