如何移动除最后一个文件之外的所有内容?

如何移动除最后一个文件之外的所有内容?

如何将除最后一个n文件之外的所有文件从移动dir1dir2

我目前这样做,将时间设置为 的近似值n,在我的例子中n=2每 10 分钟一次。

find /dir1/ -name '*.txt*' -mmin +10 -type f -exec mv "{}" /dir2/ \;

类似的命令可以工作,但我不确定,有人可以确认应该如何调整吗?

ls -1tr | head -n -2 | xargs -d '\n' mv -f --

答案1

zsh

mv dir1/**/*.txt*(D.om[3,-1]) dir2/

dir1将除了 2 个最近修改的文件之外的常规文件移至dir2.

  • **/:任意级别的子目录。
  • D:包含隐藏文件并进入隐藏目录。
  • .:仅常规文件(无符号链接、目录...),相当于finds -type f
  • om:按修改时间排序(最新的排在前面,如ls -t)。
  • [3,-1]:仅从第三个到最后一个

(您可以发出 azmodload zsh/files来获取内置函数mv,或者zargs如果您遇到arg 列表太大问题)。

POSIXly,如果不对文件名称、文件数量及其路径长度做出一些假设,就无法完成此操作。

GNUly(使用最新版本的 GNU 工具-z),您可以这样做:

find dir1 -name '*.txt*' -type f -printf '%T@\t%p\0' |
  sort -rnz | tail -zn +3 | cut -zf2- | xargs -r0 mv -t dir2

虽然 GNU sortandxargs已经有-z/-0选项数十年了,但添加-zforcuttail却是最近的事。如果您有旧版本,您可以随时执行以下操作:

find dir1 -type f -printf '%T@\t%p\0' | sort -rnz |
  tr '\n\0' '\0\n' |
  tail -n +3 | cut -f2- |
  tr '\n\0' '\0\n' | xargs -r0 mv -t dir2

请注意,虽然这些解决方案在(包括子目录)中递归查找文件dir1,但它们不会在dir2.这意味着,例如,如果同时存在 adir1/file.txtdir1/subdir/file.txt,它们最终都会被移动到dir2/file.txt,一个覆盖另一个。

答案2

由于带日期戳的文件将按照 shell glob 的顺序收集在一起(例如*.txt),因此您可以使用数组(例如在 bash 中):

n=2 ## how many of each you want to keep
txtfiles=(*.txt)
auxfiles=(*.txt_aux)
totaltxt=${#txtfiles[@]}
totalaux=${#auxfiles[@]}
movetxt=$((totaltxt-n))
moveaux=$((totalaux-n))
echo mv "${txtfiles[@]:0:movetxt}" /dir/aux2/
echo mv "${auxfiles[@]:0:moveaux}" /dir/aux2/

echo当看起来效果正确时,将最后两块取下。

答案3

一种更简单的方法:

mv `ls -tr sourcedir | head -n -2` destdir 

注意:这假设您知道目录中有两个以上的文件。如果你不确定,你可以用ls | wc -l

相关内容