加速多個目錄的隨機排序和刪除(rm)

加速多個目錄的隨機排序和刪除(rm)

在本質上是 BSD 的終端機中運行 MacOS,因此在這裡發布我的問題而不是詢問不同。我想透過隨機刪除檔案來在後續步驟中修剪圖像資料集。有些目錄有超過 100 萬張 jpg。我的資料位於主目錄中,子目錄的最大深度僅為 1:

-master
     -data1
       image.jpgs
     -data2
       image.jpgs
     -data3
       image.jpgs
     -data4
       image.jpgs
... and so forth

我找到了這個連結:

https://superuser.com/questions/1186350/delete-all-but-1000-random-files-in-a-directory

……並想出了:

for f in *.jpg; do find "$f" -type f -print0 | sort -R | tail -n +50001 | xargs -0 rm; done

雖然它確實有效,但我希望它能夠對子目錄遞歸地執行此操作,因此我不必為每個目錄手動執行此操作。所以我的問題/要求是:

  1. 我可以以某種方式優化它以加快速度嗎?
  2. sort/tail 遇到檔案少於 50,000 個的目錄時會回傳錯誤嗎?

答案1

檢查了連結的來源貼文後,看起來您的循環實際上應該是:

for d in */; do find "$d" -iname '*.jpg' -type f -print0 | sort -zR | tail -zn +50001 | xargs -0r rm; done

從目錄運行master

-z的選項是必需的,因為輸入是空分隔的。如果少於 50000 行,兩者都不會抱怨 -不關心也不會輸出任何內容,因為第 50000 行之後沒有任何內容。可能會抱怨在沒有參數的情況下運行,但是如果沒有輸入,GNU 的選項將阻止它運行(BSD xargs 不需要它,但可能不會抱怨)。sorttailsorttailrm-rxargsrm

最後但最重要的是,-zBSD tail 可能不支援 null 分隔輸入的選項。您需要 GNU tail,它可以使用自製程式安裝。

如果您的檔案名稱保證其中不包含空格、換行符號、引號、反斜線等,那麼您可能可以不使用空白分隔行。在這種情況下:

for d in */; do find "$d" -type f | sort -R | tail -n +50001 | xargs rm; done

相關內容