简体   繁体   English

替换子目录中文件中的空格

[英]Replace spaces in files within subdirectories

I have about 10,000 directories containing files.我有大约 10,000 个包含文件的目录。 I want to write a loop that iterates through each directory, picks out a.我想写一个循环遍历每个目录,挑出一个。 txt file, and replaces any spaces with a _ . txt文件,并将所有空格替换为_ How can I do this?我怎样才能做到这一点?

for f in *FOLDERS*
do
    cd "$f" && echo "Entering into $f" || { echo "Error: could not enter into $f"; continue; }
    for y in $(ls *.txt | mv "$y" "${y// /_}")
    do
        echo ${y}
    done
done 

But it doesn't work for each directory.但它不适用于每个目录。 What am i doing wrong?我究竟做错了什么?

This might be what you're trying to do:这可能是你想要做的:

#!/bin/bash

for d in */; do
    cd "$d" || exit
    for t in *\ *.txt; do
        [[ -f $t ]] && mv -i "$t" "${t// /_}"
    done
    cd ..
done

Or, if you want to do it recursively (for all subdirectories in any depth):或者,如果您想递归地执行此操作(对于任何深度的所有子目录):

#!/bin/bash

shopt -s globstar

for d in **/; do
    cd "$d" || exit
    for t in *\ *.txt; do
        [[ -f $t ]] && mv -i "$t" "${t// /_}"
    done
    cd - >/dev/null
done
  1. List all files with spaces in filenames.列出文件名中带有空格的所有文件。
  2. In that list, duplicate each line.在该列表中,复制每一行。 In the second line, change all spaces in the filename for _ .在第二行中,将文件名中的所有空格更改为_
  3. For every two lines, execute mv .对于每两行,执行mv

find *FOLDERS* -type f -name '* *.txt' -print0 |
# Duplicate the line. Replace spaces by _ in the second line.
sed -Ez 'h ; s@.*/@@ ; s@ @_@g ; G ; s@([^\x00]*)\x00(.*/)?([^/]*)@\2\3\x00\2\1@' |
# Execute mv for each two arguments.
xargs -0 -n2 echo mv -v

Select files with find , then run bash to perform the filename manipulation. find个文件,然后运行bash来执行文件名操作。

find . -type f -name '* *.txt' -exec bash -c 'for path; do
    basename="${path##*/}"
    dir="${path%/*}"
    echo mv "$path" "$dir"/"${basename// /_}"
done'  - {} +

This is fully recursive;这是完全递归的; if you don't want that you can limit the selection depth with find .如果您不想,可以使用find限制选择深度。 The other advantage to using find is you can tell for sure what files you will be operating on before you run the dangerous part.使用find的另一个好处是,在运行危险部分之前,您可以确定要对哪些文件进行操作。

The above is harmless as-is, to make it actually perform its function remove the echo before the mv .上面是无害的,让它实际执行它的 function 删除mv之前的echo

This is why your script is not working.这就是您的脚本不起作用的原因。 Consider this folder structure:考虑这个文件夹结构:

$ ls
d1  d2  d3

Now lets try to cd into each folder:现在让我们尝试cd进入每个文件夹:

$ for d in *; { cd $d; pwd; }
/tmp/d1
bash: cd: d2: No such file or directory
/tmp/d1
bash: cd: d3: No such file or directory
/tmp/d1

You have to go back to 'home' folder first:您必须先 go 回到“主”文件夹:

$ for d in *; { cd $d; pwd; cd ..; }
/tmp/d1
/tmp/d2
/tmp/d3

Or use full path in $d definition:或者在$d定义中使用完整路径:

$ for d in $PWD/*; { cd $d; pwd; }
/tmp/d1
/tmp/d2
/tmp/d3

For something fast, you will probably want Sorpigal's answer;对于快速的事情,您可能需要 Sorpigal 的回答; this will still work, but it's slower.这仍然有效,但速度较慢。

#!/bin/sh -x

find . -type f -name '* *.txt' > stack

next () {
[[ -s stack ]] && main
end
}

main () { 
line=$(sed -n "1p" stack)
echo "${line}" | tr '/' '\n' > f2
basename=$(sed -n "$p" f2)
sed -i "$d" f2
dirname=$(cat f2 | tr '\n' '/')
newname=$(echo "${basename}" | tr ' ' '_')
mv -v "${dirname}/${basename}" "${dirname}/${newname}"
sed -i "1d" stack
rm -v ./f2
next
}

end () {
rm -v ./stack
exit 0
}

next

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

相关问题 用文件中的下划线替换空格(bash) - Replace white spaces with underscores within a file (bash) 如何在子目录中查找匹配模式和替换模式的所有文件 - How to find all files in subdirectories that match pattern and replace pattern 在包含同一行字符串的工作目录(及其子目录)中搜索文件 - Searching for files, within a working directory (and subdirectories in it) containing strings on the same line 如何在文件名(也是子目录)中用一个空格替换双空格(CloudLinux Server 6.10 版) - How to replace double spaces with one space in filenames (also subdirectories) (CloudLinux Server release 6.10) 用下划线替换目录中所有文件中的空格 - Replace spaces in all files in a directory with underscores 如何使用目录和子目录中的所有文件中的另一个字符串模式替换字符串模式 - How to Replace a string pattern with another string pattern inside all files in directories and subdirectories 递归查找子目录和文件 - Recursively find subdirectories and files 如何仅跟踪工作目录中的直接后代的子目录中的 .config 文件? - How to only track .config files within subdirectories that are direct decendants from the working directory? Shell脚本可在包含特定扩展名文件的文件夹中递归列出所有子目录 - Shell script to list all subdirectories recursively within a folder that contains files with an specific extension 如何在列表中查找包含使用部分名称的目录和子目录中的所有文件,然后将它们复制到新文件夹 - How to find all files in a directory and subdirectories that contain using partial names within a list then copy them to a new folder
 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM