題 如何從命令行批量轉換文件?


我正在將音樂從Nintendo 3DS使用的專有格式轉換為wav。唯一可以轉換此專有格式的程序是一個命令行程序,它接受如下輸入:

convert.exe -o converted music.wav inputfile.differentformat

我想知道如何為文件夾中的所有文件運行此程序並保留原始文件名。例如,如果我有3個文件被調用 music1.differentformat,music2.differentformat 和 music3.differentformat 它將運行名為的命令行程序 CONVERT.EXE 並生成3個名為的wav文件 music1.wav,music2.wav,music3.wav


3
2017-10-16 04:37


起源




答案:


您可能想要為此嘗試PowerShell,而不是批處理。 PowerShell的優點在於它保留了對常規命令行實用程序的訪問權限,同時還允許您利用PowerShell附帶的更高級腳本功能和命令。

鑑於你的原始帖子,我猜你的轉換實用程序的命令語法是這樣的。

convert.exe -o converted [output filename] [input filename]

如果此語法不正確,則需要相應地調整以下腳本。

腳本模板

$MusicFolder = '[Full path to music folder]'
$InputFormat = '[Extension for input files]'
$OutputFormat = '[Extension for output files]'
Get-ChildItem "$MusicFolder\*.$InputFormat" |
ForEach-Object {
    $Filename = $_.BaseName
    $InputPath = "`"$MusicFolder\$Filename.$InputFormat`""
    $OutputPath = "`"$MusicFolder\$Filename.$OutputFormat`""
    Invoke-Expression "convert.exe -o converted $OutputPath $InputPath"
}

我沒有測試過上面的大部分內容,主要是因為我一開始並不知道你正在使用什麼實用程序,但它原則上應該工作。以下是命令和流程的一般細分:

基本概念

  • 任何形式的東西 $[Name] = [Stuff] 是一個變量賦值。
  • Get-ChildItem 是PowerShell的等價物 dir。但是,與大多數PowerShell命令一樣,關鍵的區別在於 dir 只返回控制台輸出的字符串,而 Get-ChildItem 實際上返回具有方法和屬性的對象,當對象通過管道傳遞給其他命令時可以使用這些方法和屬性。
  • 管道特徵(|將一個命令的輸出重定向到另一個命令以進行進一步處理,而不是簡單地在控制台上顯示結果。
  • ForEach-Object 獲取數組中的對象並針對每個對象運行一系列命令。
  • $_ 是PowerShell用於引用循環中正在處理的當前對象的內置變量。
  • $[Name].[Something] 指的是變量的屬性或方法 - 記住,PowerShell主要使用對象而不是簡單的字符串。
  • '[Words and Stuff]' 表示一個基本的靜態字符串。
  • "[Words and Stuff]" 也代表一個字符串。但是,雙引號是特殊的,因為它們告訴PowerShell擴展其中的變量。
    • $x = 'world'; Write-Output "Hello $x" 將輸出 Hello world
    • $x = 'world'; Write-Output 'Hello $x' 將輸出 Hello $x
  • 重音(`)是一個轉義字符,它告訴PowerShell在字符串中包含以下字符,而不是將其作為特殊字符處理,否則它將在PowerShell語法中具有功能意義。
  • Invoke-Expression 用於運行存儲為字符串的命令。這對於像你這樣的情況很有用,我們需要預先組裝外部命令的參數,然後用它的參數執行該命令。

腳本流程

  1. 前三行設置了我們稍後將用於構造文件路徑的變量。
  2. 第四行使用 Get-ChildItem 取所有文件 $MusicFolder,擴展名匹配 $InputFormat,並沿著管道轉發它們。
  3. 在第五行, ForEach-Object 將採取發送給它的文件 Get-ChildItem 並針對每個腳本塊運行其餘的腳本塊。
  4. 接下來的三行用於進一步構建我們需要提供適當參數的文件路徑詳細信息 convert.exe
    • BaseName 是文件對象的屬性,僅包含文件名 - 不包括文件夾結構和文件擴展名。
    • 請注意轉義中的雙引號 $InputPath 和 $OutputPath。這是因為實際的字符串值將圍繞它們使用雙引號,因為像您這樣的命令行實用程序很可能需要它們才能正確處理帶有空格或其他特殊字符的路徑。
  5. close-brace之前的最後一行將所有內容組合在一起並運行 convert.exe 有適當的論據。

示例腳本

$MusicFolder = 'C:\Users\Me\My Documents\Music'
$InputFormat = 'mp3'
$OutputFormat = 'wav'
Get-ChildItem "$MusicFolder\*.$InputFormat" |
ForEach-Object {
    $Filename = $_.BaseName
    $InputPath = "`"$MusicFolder\$Filename.$InputFormat`""
    $OutputPath = "`"$MusicFolder\$Filename.$OutputFormat`""
    Invoke-Expression "convert.exe -o converted $OutputPath $InputPath"
}

1
2017-10-16 05:58