SSブログ

PowerShell小僧:ファイル名の一括置換(その2)(改2) [コンピューター]

PowerShell小僧:ファイル名の一括置換(その2)(改1)
https://cheese999.blog.ss-blog.jp/2021-07-02
で紹介したスクリプト

ですが、Where-Object{$_.Name -match $TargetName1}で、正規表現を使用した
ファイル絞り込みに変更しました。

【スクリプト】
## 定数 ##
# 文字コード変換DLL
$myDLL = "C:\abcde\PowerShell\ReadJEnc\dll\net47\Hnx8.ReadJEnc.dll"
# スクリプトがある場所
$ScriptPath1 = Split-Path $MyInvocation.MyCommand.Path -Parent
# 履歴ファイル
$HistFile1 = $ScriptPath1+"\FilePath1.txt"
# 変換対象ファイル名の拡張子を除いた部分の正規表現
$TargetName1=".+_.+_.+_.+"
# 関数:文字コードを表示
function myFShChrCd1{
  [String]$result = chcp
  #$result.GetType().FullName
  # ":"で分割
  [String[]]$BUF1 = $result.Split(":")
  #$BUF1.GetType().FullName
  # 2個目の文字列
  $BUF2 = $BUF1[1]
  #$BUF2.GetType().FullName
  # 空白を削除
  [String]$ChCode1 = $BUF2.Trim()
  #Write-Host $ChCode1
  #$ChCode1.GetType().FullName
  switch ($ChCode1){
    "65001"{Write-Host "文字コードはUTF-8(65001)です。";break}
    "932"{Write-Host "文字コードはShift-JIS(932)です。";break}
    default{Write-Host "文字コードは不明です。";break}
  }
}
# 関数:何も入力されなかったら、デフォルト値を返す
Function Read-HostDefault($Prompt, $Default) {
    # デフォルト値がある時のプロンプト
    if ($Default) {
        $Prompt = "$Prompt [$Default]"
    }
    # コンソール入力
    $val = Read-Host $Prompt
    # 何も入力されなかったら、デフォルト値を返す
    if($val -eq ""){
      Return $Default
    }else{
      Return $val
    }
    # ($default,$val)[[bool]$val]
}
# 関数:ファイルの存在確認
Function myFFileExist1($myFileText1, [ref]$myFilePath1) {
  # $myFileText1 : ファイルを表す文字列
  # $myFilePath1 : ファイルパス
  # 返り値:true/false = ファイルが存在する/しない
  $myFilePath2 = $myFilePath1.Value
  # Write-Host "`$myFilePath2="$myFilePath2
  [String]$myString1 = $myFileText1 + "?"
  $myFilePath2 = Read-HostDefault $myString1 $myFilePath2
  if(-Not(Test-Path $myFilePath2)){
    $myString1 = $myFileText1 + "が存在しません。"
    Write-Host $myString1
    Write-Host "ファイルパス="$myFilePath2
    Return $FALSE
  }else{
    $myFilePath1.Value = $myFilePath2
    Return $TRUE
  }
}
# 関数:文字コード判別
Function myMojiCode1($Name1){
  If($Name1.IndexOf("ShiftJIS") -ge 0){
    $myMojiCoding1 = "Default"
  }ElseIf($Name1.IndexOf("UTF-8") -ge 0){
    $myMojiCoding1 = "UTF8"
  }ElseIf($Name1.IndexOf("EUCJP") -ge 0){
    $myMojiCoding1 = -1
  }ElseIf($Name1.IndexOf("ASCII") -ge 0){
    $myMojiCoding1 = "ASCII"
  }Else{
    $myMojiCoding1 = -1
  }
  Return $myMojiCoding1
}
# 関数:終了処理
Function End_Process1($CurrentPath1){
  # 現在のパス
  Write-Host "現在のパス(Get-Location)"
  Get-Location
  # 入力待ち
  Read-HostDefault "OK?" > $null
  # スクリプト実行前のパスに戻る
  Write-Host "スクリプト実行前のパスに戻ります。"
  Set-Location $CurrentPath1
  # 現在のパス
  Write-Host "現在のパス(Get-Location):スクリプト実行前"
  Get-Location
  write-host "文字コードをShift-JIS(932)に変更します。"
  # 入力待ち
  Read-HostDefault "OK?" > $null
  # 文字コードをShift-JISに変更
  chcp 932
  # 文字コードを表示
  myFShChrCd1
}
# ここから本体コード
# DLLを読み込み
# Write-Host "`$myDLL="$myDLL
$myAnswer1 = myFFileExist1 -myFileText1 "文字コード変換DLL" -myFilePath1 ([ref]$myDLL)
if($myAnswer1 -eq $FALSE){exit} # DLLが存在しない場合は終了
[Reflection.Assembly]::LoadFile($myDLL) > $null
# 文字コードをUTF-8に変更
chcp 65001
# 文字コードを表示
myFShChrCd1
# 現在のパス
$CurrentPath1 = Get-Location
Write-Host "現在のパス="$CurrentPath1
Write-Host "スクリプトがある場所="$ScriptPath1
# 変換対象ファイル名
$TargetName1 = Read-HostDefault "変換対象ファイル名?" $TargetName1
Read-HostDefault "OK?" > $null # 入力待ち
# 履歴変数の配列宣言
$PrevPath1 = @()
# 履歴ファイル
$myAnswer1 = myFFileExist1 -myFileText1 "履歴ファイル" -myFilePath1 ([ref]$HistFile1)
if($myAnswer1 -eq $FALSE){
  # 履歴ファイルが存在しない
  $PrevPath1 += $CurrentPath1 # 履歴変数にカレントパスを追加
}else{
  # 履歴ファイルが存在する場合
  # 履歴ファイルの文字コード確認
  $file=Get-Item $HistFile1
  $reader=new-object Hnx8.ReadJEnc.FileReader($file)
  [String]$ReaderName1 = $reader.Read($file).Name
  Write-Host "`$reader.Read(`$file).Name="$ReaderName1
  $myMojiCoding1 = myMojiCode1($ReaderName1)
  Write-Host "`$myMojiCoding1="$myMojiCoding1
  $myLine1 = (Get-Content -LiteralPath $HistFile1|Measure-Object -Line).Lines
  Write-Host "履歴ファイルの行数="$myLine1
  If($myMojiCoding1 -eq -1){
    # 履歴ファイルの文字コードが不明な場合
    Write-Host "履歴ファイルの文字コードが不明です。"
    $PrevPath1 += $CurrentPath1 # 履歴変数にカレントパスを追加
  }Else{
    # 履歴ファイルの文字コードが明確な場合
    # 履歴ファイルを履歴変数(配列)に読み込み
    $PrevPath1=Get-Content $HistFile1 -totalcount 1 -Encoding $myMojiCoding1
    $OutputEncoding = [console]::OutputEncoding;
    Write-Host "`$PrevPath1=$PrevPath1"
    $PrevPath1=(Get-Content $HistFile1 -Encoding $myMojiCoding1) -as [string[]]
  }
}
[int]$myCNT1 = 1 # 履歴カウンタ(foreachループ)
[int]$myCNT2 = 1 # 履歴書き込みカウンタ
$ErrFlg1 =$FALSE # エラーフラグをリセット
# 履歴の数だけ繰り返し
foreach ($MyPrev1 in $PrevPath1){
  # ファイルがあるフォルダを入力
  $MyFilePath1 = Read-HostDefault "($myCNT1/$myLine1)ファイル名変更の対象ファイルがあるフォルダ?" $MyPrev1
  if(-Not(Test-Path $MyFilePath1)){
    # フォルダが存在しない
    Write-Host "フォルダが存在しません。"
    $ErrFlg1 = $TRUE # エラーフラグをセット
  }else{
    # フォルダが存在する場合
    # ファイルがあるフォルダへ移動
    Set-Location -LiteralPath $MyFilePath1
    # 対象ファイル数が0の場合、エラーフラグをセット
    $myFileCount1 =(Get-ChildItem|Where-Object{$_.Name -match $TargetName1}|Measure-Object).Count
    if($myFileCount1 -eq 0){
      Write-Host "変換対象ファイルがありません。"
      $ErrFlg1 = $TRUE # エラーフラグをセット
    }else{
      Write-Host "変換対象ファイル"
      Get-ChildItem|Where-Object{$_.Name -match $TargetName1}
      Write-Host "ファイル数="$myFileCount1
      $myInput1 = Read-HostDefault "ファイル名を変更しますか(Y/N)?" "N"
      # Y以外なら、エラーフラグをセット
      if($myInput1 -ne "Y"){
        $ErrFlg1 = $TRUE
        Write-Host "Y以外が入力されました。"
      }
    }
  }
  # エラーフラグが偽なら、ファイル名の連番の開始番号を入力
  if($ErrFlg1 -eq $FALSE){
    [String]$StartNo = Read-HostDefault "ファイル名の連番の開始番号?" 1
    # ヌル判定
    # if ([String]::IsNullOrEmpty($StartNo)){
    # Write-Host "開始番号に何も入力されなかったので、開始番号=1とします。"
    # [string]$StartNo = "1"
    # Read-HostDefault "OK?" > $null # 入力待ち
    # }
    # 変換後の整数変数
    [Int]$StartNo1 = 0
    # 整数変換
    [Bool]$Result1 = [int]::TryParse($StartNo, [ref]$StartNo1)
    if($Result1 -eq $FALSE){
      $ErrFlg1 = $TRUE # エラーフラグをセット
      Write-Host "開始番号="$StartNo" に整数以外が入力されました。"
      Read-HostDefault "OK?" > $null # 入力待ち
    }
  }
  # エラーフラグが偽なら、新しいファイル名の確認
  if($ErrFlg1 -eq $FALSE){
    $Str_array1 = @() # 配列
    $Str_array1 = $TargetName1 -Split "_";
    [String]$String1 = "新しいファイル名:" + $Str_array1[0] + "_" + $Str_array1[1] + "_" + $Str_array1[2]
    $String1 = $String1 + "_" + $StartNo1.tostring("000") + ".xxx でよろしいですか(Y/N)?"
    $myInput1 = Read-HostDefault $String1 "N"
    if($myInput1 -ne "Y"){
      $ErrFlg1 = $TRUE # エラーフラグをセット
      Write-Host "Y以外が入力されました。"
    }
  }
  # エラーフラグが偽なら、ファイル名変換と履歴書込を実施
  if($ErrFlg1 -eq $FALSE){
    # ???_???_???_001.???, ???_???_???_002.??? と昇順で名前を付け替える
    Write-Host "番号 変更前 変更後"
    Get-ChildItem | Where-Object{$_.Name -match $TargetName1} | Sort-Object Name | ForEach-Object {$myCNT3 = $StartNo1} {
      $String1 = [System.IO.Path]::GetFileNameWithoutExtension($_);
      $Str_array1 = $String1 -Split "_";
      $String1 = $String1 + $_.extension
      $NewFilename = $Str_array1[0] + "_" + $Str_array1[1] + "_" + $Str_array1[2] + "_" + $myCNT3.tostring("000") + $_.extension
      Write-Host $myCNT1" "$myCNT3" "$String1" "$NewFilename;
      Rename-Item $_ $NewFilename;
      $myCNT3++
    }
    Read-HostDefault "OK?" > $null # 入力待ち
    # ファイルパスをテキストファイルに出力
    Write-Host "ファイルパスを履歴ファイルに出力"
    if($myCNT2 -eq 1){
      # 初回は新規書き込み
      Set-Content -Encoding UTF8 -LiteralPath $HistFile1 -Value $MyFilePath1
    }else{
      # 2回目以降は追記
      Add-Content -Encoding UTF8 -LiteralPath $HistFile1 -Value $MyFilePath1
    }
    $myCNT2++
  }
  $myCNT1++
}
End_Process1 $CurrentPath1
ヤバイぜ!(6)  コメント(1) 
共通テーマ:日記・雑感

ヤバイぜ! 6

コメント 1

cheese999

ヤバイぜ! ありがとうございます(^_0)ノ
by cheese999 (2021-07-08 06:08) 

コメントを書く

お名前:[必須]
URL:
コメント:
画像認証:
下の画像に表示されている文字(英大文字の「オー」、英小文字の「ユー」、アラビア数字の「ハチ」、アラビア数字の「イチ」、アラビア数字の「ニ」)を入力してください。

Facebook コメント

この広告は前回の更新から一定期間経過したブログに表示されています。更新すると自動で解除されます。