使用路徑名重命名文件

使用路徑名重命名文件

我的子資料夾中有一個 .bdf 檔。所有 .bdf 都有相同的名稱:Loads.bdf

例子:

/home/user/folderxx/folderxxx/Load.bdf
/home/user/folderxx/folderxxx/Load.bdf

我需要找到(並複製到新資料夾)所有 Load.bdf 檔案並用其路徑名稱重命名它們。

範例:在預期的操作之後,它應該會顯示類似這樣的內容。

folder001_folderAAA_Load.bdf
folder002_folderBBB_Load.bdf

答案1

我將使用(“多次移動”)包mcp中的工具:mmv

mcp '/home/user/*/*/Load.bdf' '#1_#2_Load.bdf'

#1第二個字串中的等#2將替換為第一個字串中對應的第一個、第二個等通配符的內容。注意,路徑用單引號括起來,以便通配符由 解釋mcp,而不是由 shell 解釋。

使用顯示的命令,檔案將被複製到目前目錄。如果替換mcpmmv,文件將被移動。

答案2

使用prename(在許多系統上別名為rename)可以在不多次運行mvor的情況下完成此操作cp

cd /home/user
find . -type f -name 'Loads.bdf' -exec \
  prename -n 's:^./::; s:/:_:g; s:^:destination/:' {} +

-n當您確定這正在移動您想要的檔案時,請刪除。

更新

要複製檔案而不是移動它們,最快的方法是先使用cpiopax複製,然後像以前一樣重新命名。例如(使用 GNU cpio):

cd /home/user
find . -type f -name 'Loads.bdf | cpio -p --make-directories destination

cd destination
find . -type f -name 'Loads.bdf' -exec  prename -n 's:^./::; s:/:_:g' {} +

請注意,雖然pax既是 POSIX 又是 LSB,並且cpio不再是 POSIX,但cpio仍然是許多系統中常見的程式。

find要使用 GNU /處理帶有換行符的檔名,cpio可以添加-print0find-0cpio.

更新2

解決pax方案是一行(不包括cd):

cd /home/user
find . -name 'Loads.bdf' | cut -d/ -f 2- | pax -rws ':/:_:g' destination

或對於任何檔案名稱(和 GNU find):

find /home/user -name 'Loads.bdf' -printf '%P\0' | pax -0rws ':/:_:g' destination

答案3

如果您碰巧需要在沒有其他一些答案中提到的工具(例如 mcp 和 mmv 或 prename)的系統上執行此操作,並且您想完全在 shell 中執行此操作,則可以執行某些操作喜歡:

#!/usr/bin/env bash

oldpath="/home/user"
newpath="/home/user/newfolder"

for file in $(find $oldpath -type f -name Load.bdf); do
        shortname=${file#$oldpath/}
        newname="$newpath/${shortname//\//_}"
        if [ -f $newname ]; then
                echo "$newname already exists."
        else
                echo "copy: $file"
                echo "  --> $newname"
                cp $file $newname
        fi
done

Load.bdf該腳本將查找目錄中指定的所有文件oldpath,將目錄名稱合併為新文件名,然後將它們複製到目標目錄。我們還可以檢查已複製的檔案是否存在,以防您需要多次執行它,並且我們不需要再次複製所有檔案。

最終的目錄結構將如下所示:

bash$ find . -type f
/home/user/folder001/folderAAA/Load.bdf
/home/user/folder002/folderBBB/Load.bdf
/home/user/folder003/folderCCC/Load.bdf
/home/user/newfolder/folder001_folderAAA_Load.bdf
/home/user/newfolder/folder002_folderBBB_Load.bdf
/home/user/newfolder/folder003_folderCCC_Load.bdf

答案4

env - sh <<\SCRIPT

    t=/home/user/target f=folder
    cd "${t%/*}" && mkdir -p "$t"
    set -- $f??/$f???/Load.BDF
    while [ -e "$1" ] ; do
        cp "$1" "$t/$(IFS=/
            printf '%s_%s_%s\n' $1)"
    shift ; done

SCRIPT

我認為這都是完全可移植的 shell 腳本 - 儘管我一開始對此表示懷疑,但完成起來非常簡單。

相關內容