跑完重新命名腳本才發現兩個檔案撞在一起;另一批照片的序號位數設成 3,腳本裡混著 6 個 8 字元的名字。這不是規則沒生效,而是規則跟表單上寫的約束不是一回事。
批次重新命名 範本裡那幾個函式抽出來跑一遍,落點很具體:位數只是下限,編號插在主名與後綴之間,手改過的那一行當下根本不跑避讓。
位數設的是下限,不是寬度
「序號位數」那欄寫著 min="0" max="9",看著像被約束住了,真正執行的只有 brPad(T300 起):位數不夠時補 0,從來不裁。brPad(999,3) 得 999,brPad(10000,3) 得 10000。那兩個表單屬性對 JS 沒有約束力,pad=9 得 000000001.jpg,填 12 得 000000000001.jpg,填 -2 也照程式碼生效。
| 規模 / 位數 | 字元數分佈 | 讀法 |
|---|---|---|
| 105 個 / pad=2 | 6 字元 99 個,7 字元 6 個 | 第 100 個起整列變寬 |
| 1005 個 / pad=3 | 7 字元 999 個,8 字元 6 個 | 999 之後只能多一位 |
| 12 個 / pad=12 | 16 字元 12 個 | 表單的 max=9 不被執行 |
重名:編號插在後綴之前
conflict 的預設檔 auto 遇到一堆行指向同一個名字時,不報錯、不跳過、也不覆蓋先到的那一行,而是把後撞的改成「主名 + 空格 + (2) + 原樣的點和後綴」,行內標「重名,已自動追加編號」。50 行全撞時末行是 same.txt (50).txt,帶標註的只有 49 行。編號落在主名與原後綴之間:a.b.tar.gz 撞車後追加出來的是 x.tar.gz (2).gz。
判撞名用 toLowerCase,Photo.jpg / PHOTO.JPG / photo.jpg 算同一個坑,避讓後寫成 same.txt (2).JPG——編號加上了,後綴大小寫仍跟著各行原樣;另一檔 skip 寫「重名,已保持原名」。
手改與關掉的那一行:避讓的兩個例外
行內改名字走 brEditRow(T561-571),只重算統計條和腳本,不跑 brDedupe。把 p.txt 與 q.txt 兩行都手打成 p.txt,表格當場兩條同名,匯出也兩條都收,腳本裡那條 Rename-Item -LiteralPath 'q.txt' -NewName 'p.txt' 改的是磁碟上已經存在的名字。要等下一次規則變化,brDedupe 才把它補成 p (2).txt。
關掉某一行的「改名」,它不再產新名,卻照樣先佔住原名:x.txt 與 b.txt 兩行,find 寫 x、repl 寫 b,再把 b.txt 那行關掉,活著的 x.txt 會被推成 b (2).txt。這一頁 0 次磁碟寫回,沒有 undo、redo、history,改名全靠匯出的 ps1 / bat / sh。
後綴的四條口徑
brSplitName 只認最後一個點,a.tar.gz 的主名是 a.tar、後綴是 gz;.gitignore 這類點開頭的名字判成「無副檔名」,前導點保留。大小寫不越界:選「全部小寫」時 DSC Photo JPG.jpeg 出來是 dsc-photo-jpg.jpeg,尾巴上的 .jpeg 一動不動,後綴要小寫必須另外選「統一小寫」。
沒勾「連副檔名一起取代」時,取代只餵最後一個點之前的主名:find 寫 \..*、repl 留空,a.tar.gz 只得到 a.gz,因為程式又把原後綴接回末尾;find 寫成字面的 .gz 時輸出完全不變,勾上開關才得到 a。反向的坑是副檔名選「強制指定」卻不填值,Photo.JPG、doc.pdf 變成 Photo、doc,後綴整段消失,還不進「規則有問題」統計。
取代串裡的 $ 不是字面量
勾上「按正則處理」後,repl 那欄的 $ 走 JS 取代語義。find 寫 b、repl 寫 $`X,abc.jpg 變成 aaXc.jpg:匹配之前那段 a 被整塊塞進取代串;寫 $&$& 得 abbc.jpg,寫 $9 而沒有第 9 組時原樣留 a$9c.jpg。字面模式裡按字面處理。
正則寫錯不會把頁面弄崩:brReplace 回傳一個哨兵串(T395),行內提示「正則運算式寫錯了」並保留原名,代價是判壞的整列不進匯出。3 個檔案、find 寫 (:3 行都留在原名並標紅,統計條「規則有問題:3」,匯出 0 行、腳本框是空的,打包只彈「沒有可匯出的檔案」。
上限和另外幾個硬頂
一次最多收 2000 個。拖 2005 個進去,files 記 2000、表格 2000 行,預覽只畫前 400 行,末尾補一句「另有 1600 行未在預覽裡顯示」。Rename-Item、ren、mv -n 各 2000 條,匯出也是 2000 行。
另外三個數字也管著名字落地。主名的 160 字元硬頂:204 字元的原名截到 160 再接回 .txt,最終整名 164 字元,行內寫「名稱過長,已截到 160 字元」。Windows 保留名共 22 項(CON、PRN、AUX、NUL 加 COM 與 LPT 各 1 到 9),命中時加底線前綴,CONSOLE.txt 和 LPT10 不判定。非法字元勾了清理是刪掉,取消勾選換成底線,note 仍寫「已去掉非法字元」。
三個當場被問到的
Q:位數設小了,長名字會不會被截斷?
不會。brPad 只在不夠長時補 0,1005 個檔案配 pad=3 依然留下 6 個 8 字元的名字;真正會截的是主名那條 160 字元硬頂。
Q:手改過一行之後,重名還會自動避讓嗎?
當下不會。brEditRow 不跑 brDedupe,兩條同名可以一起進匯出,要等下一次規則變化才被補成 p (2).txt。點任意範本按鈕還會走 T679-683 那條無條件賦值,把手改過的行一起重算掉,沒有還原入口。
Q:匯出的批次處理遇到同名會自己停下來嗎?
腳本頭部寫著「重名會報錯並停下」,但產生的 .bat 實測只有 @echo off、chcp 65001 >nul、rem 頭加逐條 ren 共 13 行,沒有 errorlevel、if exist、exit 任何一句,ren 撞名只印一行錯誤、後面的命令接著跑。帶「已有同名就不覆蓋」語義的是 sh 的 mv -n;更通用的引號與中斷口徑,批次建目錄那篇已經踩過一遍。
匯出去跑之前看一遍
- 把目標名那一列排一次序找重複,手改過的行沒參與避讓。
- 看序號那一列的字元數分佈,pad=3 裡混進 8 字元是進位,不是設定丟了。
- 副檔名選「強制指定」就必須填值,留空等於整段刪掉後綴。
- 勾了正則就把「規則有問題」讀到 0 為止,壞的那幾行不進匯出;取代串裡
$打頭的寫法先用正則測試對一遍結果。