路径名中的空格会导致在 Bash 中查找时出现问题。有什么*简单的*解决方法吗?

发布于 2024-09-27 10:48:04 字数 325 浏览 1 评论 0原文

有什么方法可以更改以下字符串,这样当文件/文件夹中包含空格时我就不会遇到任何问题?

files=`find ~/$folder -name "*@*" -type f`

我希望有一个解决方案,不必涉及更改代码的其他部分,但需要更改这行代码,因为除了这个小细节之外,一切似乎都工作正常。

谢谢

编辑:这是更详细的代码:

abc=( $(find "$pasta" -name "$ficheiro_original@*" -type f) )
abc_length=${#abc[@]}

Is there any way to change the following string so I don't get any problems when there are files/folders with spaces in them?

files=`find ~/$folder -name "*@*" -type f`

I'd prefer if there was a solution that wouldn't have to involve having to change other parts of my code but this line of code, as everything seems to be working correctly, apart from this minor detail.

Thanks

EDIT: Here is the code in a bit more detail:

abc=( $(find "$pasta" -name "$ficheiro_original@*" -type f) )
abc_length=${#abc[@]}

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(5

在巴黎塔顶看东京樱花 2024-10-04 10:48:04

如果您稍后在脚本中不使用这些文件名,只需迭代它们并即时处理即可。

find ~/$folder -name "*@*" -type f | while read -r FILE
do
  echo "do you stuff"
done

否则,您可以设置 IFS

IFS=

更新:

$ IFS=
\n'
files=$(find ~/$folder -name "*@*" -type f)

更新:


\n'
$ a=($(find . -type f ))
$ echo ${#a[@]}
14
\n' files=$(find ~/$folder -name "*@*" -type f)

更新:

If you are not using those file names later in your script , just iterate them and process on the fly.

find ~/$folder -name "*@*" -type f | while read -r FILE
do
  echo "do you stuff"
done

otherwise, you can set IFS

IFS=

Update:

$ IFS=
\n'
files=$(find ~/$folder -name "*@*" -type f)

Update:


\n'
$ a=($(find . -type f ))
$ echo ${#a[@]}
14
\n' files=$(find ~/$folder -name "*@*" -type f)

Update:

深爱成瘾 2024-10-04 10:48:04

您必须进行一些更改,但要处理任意名称,请考虑使用 GNU Find 选项 -print0 等。

find ~/$folder -name "*@*" -type f -print0 |
while read -d '^@' file
do
    echo "<<$file>>"
done

(其中表示为“^@”的单字节实际上是 ASCII NUL(“\0”;使用 Control-V 输入 Control-Shift-@ )。

find ~/$folder -name "*@*" -type f -print0 |
while read -d '' file
do
    echo "<<$file>>"
done

分隔符的空字符串表示“使用零字节 ASCII NUL 作为分隔符”,适合解析“find ... -print0”输出(谢谢。 Dennis Williamson 获取提示。)

这允许您读取任意名称,您可能应该使用 bash 数组来读取。保留名称,但这意味着脚本中需要进行一些更改

(考虑到只需要担心空格的注释响应,这可能有点过头了,尽管使用 read 来处理具有名称的行是可行的。操作的关键部分,使用数组可能会让生活变得更简单。)

You'd have to make some changes, but to deal with arbitrary names, think in terms of using the GNU Find option -print0, etc.

find ~/$folder -name "*@*" -type f -print0 |
while read -d '^@' file
do
    echo "<<$file>>"
done

(Where the single byte represented as '^@' is actually an ASCII NUL ('\0'; enter with Control-V Control-Shift-@).

find ~/$folder -name "*@*" -type f -print0 |
while read -d '' file
do
    echo "<<$file>>"
done

The empty string for the delimiter means 'use the zero byte, ASCII NUL, as the delimiter' and is appropriate for parsing 'find ... -print0' output. (Thanks Dennis Williamson for the tip.)

This allows you to read any arbitrary names. You should probably use a bash array to hold the names, but that implies some changes further down the script.

(Given the comment response that only spaces have to be worried about, this might be overkill, though using read to process lines with the names is a key part of the operation, and using an array would probably make life simpler.)

三寸金莲 2024-10-04 10:48:04

如果您需要名称中可能包含空格的文件列表,则几乎必须将它们存储为数组,而不仅仅是字符串。使用如下内容创建数组:

saveIFS="$IFS"; IFS=

然后您必须修改脚本的其余部分以将文件用作数组而不是字符串,并且它(和其他文件名)应始终用双引号引起来以保留空格被误认为是分隔符。例如,在您当前使用 $files 的任何地方,请将其替换为 "${files[@]}"

ls "${files[@]}"
for f in "${files[@]}"; do
    ls "$f"
done
echo "found ${#files[@]} files" 
\n'; files=( $(find ~/"$folder" -name "*@*" -type f) ); IFS="$saveIFS"

然后您必须修改脚本的其余部分以将文件用作数组而不是字符串,并且它(和其他文件名)应始终用双引号引起来以保留空格被误认为是分隔符。例如,在您当前使用 $files 的任何地方,请将其替换为 "${files[@]}"

If you need a list of files that might have spaces in the names, you pretty much have to store them as an array, rather than just a string. Create the array with something like this:

saveIFS="$IFS"; IFS=

and then you'll have to modify the rest of the script to use files as an array rather than a string, and it (and other filenames) should always be in double-quotes to keep spaces from being mistaken as separators. For instance, anyplace you're currently using $files, replace that with "${files[@]}"

ls "${files[@]}"
for f in "${files[@]}"; do
    ls "$f"
done
echo "found ${#files[@]} files" 
\n'; files=( $(find ~/"$folder" -name "*@*" -type f) ); IFS="$saveIFS"

and then you'll have to modify the rest of the script to use files as an array rather than a string, and it (and other filenames) should always be in double-quotes to keep spaces from being mistaken as separators. For instance, anyplace you're currently using $files, replace that with "${files[@]}"

野生奥特曼 2024-10-04 10:48:04

这是另一种无需更改其余代码即可解决的方法:

# files=($(find))
eval "files=($(find -printf '"%h/%f" '))"

for f in "${files[@]}"; do
  echo "$f"
done

它很脏,不适用于具有特殊字符的文件名,例如 "。它使用 eval 来评估字符串Bash 数组的 -printffind 来形成该字符串,

我个人更喜欢更改 $IFS,仅供参考。

Here is another way to get around without changing the rest of code:

# files=($(find))
eval "files=($(find -printf '"%h/%f" '))"

for f in "${files[@]}"; do
  echo "$f"
done

It's dirty and will not work for filename with special characters, e.g. ". It uses eval to evaluate a string of a Bash array and -printf of find to form that string.

I personally prefer changing $IFS, just FYI.

成熟稳重的好男人 2024-10-04 10:48:04

要将带有空格的文件名读取到 Bash 数组变量中,您也可以使用“read”内置命令:

printf '%q\n' "$IFS"

IFS=

请注意,新设置的 IFS 变量的范围仅限于执行 read 命令(这会保留原始 IFS 变量)完好无损的)。

\n' read -r -d "" -a abc <<< "$(find ~/$folder -name "*@*" -type f)" IFS=

请注意,新设置的 IFS 变量的范围仅限于执行 read 命令(这会保留原始 IFS 变量)完好无损的)。

\n' read -r -d "" -a abc < <(find ~/$folder -name "*@*" -type f) # alternative abc_length=${#abc[@]} for ((i=1; i <= ${#abc[@]}; i++)); do echo "$i: ${abc[i-1]}"; done printf '%q\n' "$IFS"

请注意,新设置的 IFS 变量的范围仅限于执行 read 命令(这会保留原始 IFS 变量)完好无损的)。

To read file names with spaces into a Bash array variable, you could use the "read" builtin command as well:

printf '%q\n' "$IFS"

IFS=

Note that the scope of the newly set IFS variable is limited to the execution of the read command (which leaves the original IFS variable intact).

\n' read -r -d "" -a abc <<< "$(find ~/$folder -name "*@*" -type f)" IFS=

Note that the scope of the newly set IFS variable is limited to the execution of the read command (which leaves the original IFS variable intact).

\n' read -r -d "" -a abc < <(find ~/$folder -name "*@*" -type f) # alternative abc_length=${#abc[@]} for ((i=1; i <= ${#abc[@]}; i++)); do echo "$i: ${abc[i-1]}"; done printf '%q\n' "$IFS"

Note that the scope of the newly set IFS variable is limited to the execution of the read command (which leaves the original IFS variable intact).

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文