将数千个文件放在以特定方式命名的文件夹中

将数千个文件放在以特定方式命名的文件夹中

我有一个名为 test 的文件夹,里面只有 jpeg 文件。数千个文件。我需要将这些数千个文件(命名为 1.jpg、2.jpg...345623.jpg)放入子文件夹中,这些子文件夹的名称将类似于 001000、002000,每个子文件夹包含 1000 个文件。因此,我需要以最高效的方式将所有 jpg 文件从 test 文件夹移动到包含每个 1000 个 jpg 文件的子文件夹中。

我目前拥有的是:

i=1;while read l;do mkdir $i;mv $l $((i++));done< <(ls|xargs -n1000)

答案1

find . -type f \
| split -l 1000 -a 3 --numeric-suffixes=1 \
  --filter='target="${FILE}000"; mkdir "$target" && xargs -d "\n" mv -t "$target"' \
  - ''

解释:

  • find . -type f查找文件(也在子目录中,但我相信在您的情况下还没有子目录)。
  • split -l 1000 -a 3 --numeric-suffixes=1 ... - ''从其标准输入 ( -) 读取数据,并将数据拆分为块,每块长 1000 行 ( -l 1000)。每个块都有一个关联的“名称”,由空前缀 ( '') 和数字后缀组成,从 1 ( ) 开始,--numeric-suffixes=1长度为 3 ( -a 3)。此时的名称实际上是001002依此类推。
  • --filter=...为每个块单独运行指定的命令,相应的名称可用作$FILE。要运行的命令是

    target="${FILE}000"; mkdir "$target" && xargs -d "\n" mv -t "$target"
    
    • target="${FILE}000"将名称(如001或)转换002为您想要的未来目录名称(001000002000等)并将其存储在target变量中。
    • mkdir "$target"创建具有所需名称的新目录。
    • xargs -d "\n" ...读取整个块(1000 个文件路径,或最后一个块中更少)并使用每一整行(换行符作为分隔符-d "\n":)作为后续命令的参数。
      • mv -t "$target"将对象(传递的xargs)移动到新创建的目录。

笔记:

  • 该命令不关心文件名。345623.jpg不一定以 结尾346000/。可能的原因:
    • find无法排序;但即使你把 放在和sort -n之间,也可能......findsplit
    • 编号有间隙。split无论如何都会占用 1000 个条目(除非它是最后一个块;如果是,则为 1000 个或更少)。
  • mkdir ... && xargs ...xargs如果失败则不会运行mkdir(注意现有目录)。
  • 使用cp -l -t "$target"而不是mv -t "$target"在目录中创建硬链接,使当前目录中已经存在的条目保持完整。这样,如果出现问题,只需删除rm -r目录并重新开始。使用mv,如果任务中断,您将最终发现一些文件被移动,而另一些则没有;这可能会很混乱。
  • 我认为-a 3它不会让您通过999999000在附加尾随零之后)。如果split需要创建更多块,它将在作业中途失败。因此,999在运行命令之前请确保足够。
  • 带有换行符的名称会破坏代码(一般来说,您的文件名看起来不错)。

相关内容