2018年6月1日に掲載さと回答のいずれも、例外とによって投稿単一のコマンドラインのfoxidrive、実際にすべてのファイルとすべてのフォルダ/ディレクトリを削除しません%PathToFolder%
。それが、フォルダーのすべてのファイルとサブフォルダーを削除する非常にシンプルな単一のコマンドラインでさらに1つの回答を投稿する理由であり、DELを使用して他のすべての回答が2018-06-01に投稿された理由を説明するより複雑なソリューションを持つバッチファイルも同様ですそしてFORとRDは、完全にフォルダをクリーンアップできませんでした。
もちろん、バッチファイルでも使用できる単純な単一のコマンドラインソリューション:
pushd "%PathToFolder%" 2>nul && ( rd /Q /S "%PathToFolder%" 2>nul & popd )
このコマンドラインには、3つのコマンドが順番に実行されます。
最初のコマンドPUSHDはスタック上の現在のディレクトリパスをプッシュし、次に%PathToFolder%
コマンドプロセスを実行するための現在のディレクトリを作成します。
コマンド拡張はデフォルトで有効になっているため、これはデフォルトでUNCパスでも機能します。この場合、PUSHDは指定されたネットワークリソースを指す一時的なドライブ文字を作成し、新しく定義されたドライブ文字を使用して現在のドライブとディレクトリを変更します。
指定されたディレクトリがまったく存在しない場合、PUSHDはSTDERRを処理するために次のエラーメッセージを出力します。
指定されたパスが見つかりません。
このエラーメッセージは2>nul
、デバイスNULにリダイレクトすることで抑制されます。
次のコマンドRDは、現在のコマンドプロセスの現在のディレクトリを指定されたディレクトリに変更できた場合、つまり指定されたディレクトリが存在する場合にのみ実行されます。
オプション付きのコマンドRDは、指定されたディレクトリーに隠し属性または読み取り専用属性が設定されたファイルまたはフォルダーが含まれている場合でも、すべてのサブディレクトリーとともに静かにディレクトリー/Q
を/S
削除します。システム属性は、ファイルまたはフォルダーの削除を決して防ぎません。
削除されないもの:
実行中のプロセスの現在のディレクトリとして使用されるフォルダ。実行中のプロセスの現在のディレクトリとしてフォルダが使用されている場合、そのようなフォルダへのフォルダツリー全体を削除することはできません。
実行中のアプリケーション/プロセスによって開かれている間のファイルの削除を防ぐために、ファイルを開くときにファイルアクセス許可が設定されている実行中のプロセスによって現在開かれているファイル。このような開かれたファイルは、開かれたファイルへのフォルダツリー全体の削除も防ぎます。
現在のユーザーがファイル/フォルダーを削除するために必要な(NTFS)権限を持っていないファイル/フォルダー。これにより、このファイル/フォルダーへのフォルダーツリーも削除されなくなります。
フォルダーを削除しない最初の理由は、このコマンドラインで、フォルダー自体ではなく、指定したフォルダーのすべてのファイルとサブフォルダーを削除するために使用されます。このフォルダーは、コマンドプロセスを実行するために一時的に現在のディレクトリになり、フォルダー自体の削除が防止されます。もちろんこれにより、コマンドRDによってエラーメッセージが出力されます。
別のプロセスによって使用されているため、プロセスはファイルにアクセスできません。
ファイルはここでは間違った用語です。実際には、フォルダーは別のプロセス(コマンドRDを実行した現在のコマンドプロセス)によって使用されているためです。まあ、実際には、フォルダーはファイルシステムの特別なファイルで、このエラーメッセージを説明するファイル属性ディレクトリがあります。しかし、ファイルシステム管理に深く入り込みたくありません。
このエラーメッセージは、上記の3つの理由により発生する可能性のある他のすべてのエラーメッセージと同様に2>nul
、ハンドルSTDERRからデバイスNULにリダイレクトすることで抑制されます。
3番目のコマンドPOPDは、コマンドRDの終了値とは関係なく実行されます。
POPDは、PUSHDによってプッシュされたディレクトリパスをスタックからポップし、コマンドプロセスを実行するための現在のディレクトリをこのディレクトリに変更します。つまり、初期の現在のディレクトリを復元します。POPDはによって作成された一時的なドライブ文字を削除PUSHD UNCフォルダパスの場合を。
注: 初期の現在のディレクトリが、削除するディレクトリのサブディレクトリで、存在しないものである場合、POPDは警告なしに初期の現在のディレクトリを復元できません。この特別なケースで%PathToFolder%
は、現在のディレクトリのままです。したがって、のサブディレクトリからではなく、上記のコマンドラインを実行することをお勧めします%PathToFolder%
。
もう一つの興味深い事実:
私はまた、ローカルディレクトリを共有することにより、UNCパスを使用してコマンドラインを試みたC:\Temp
共有名とTemp
し、UNCパス使用して\\%COMPUTERNAME%\Temp\CleanTest
環境変数に割り当てられたPathToFolder
コマンドラインを実行している上、現在のディレクトリが共有ローカルのサブディレクトリがある場合は、Windows 7上をフォルダは、UNCパスを使用してアクセス、すなわちC:\Temp\CleanTest\Subfolder1
、Subfolder1
によって削除されるRD、次のPOPDは、製造中に静かに失敗しC:\Temp\CleanTest\Subfolder1
、再度、その結果、現在のディレクトリZ:\CleanTest
実行コマンド処理のための現在のディレクトリとして残りを。したがって、この非常に特殊なケースでは、一時ディレクトリは、現在のディレクトリが次のように変更されるまで残ります。cd /D %SystemRoot%
実際に存在するローカルディレクトリに。残念ながら、POPDは、初期の現在のディレクトリの復元に失敗した場合、0より大きい値で終了せず、POPDの終了コードだけを使用してこの非常に特殊なエラー状態を検出できません。ただし、UNCパスは通常ローカルファイルやフォルダーへのアクセスには使用されないため、この非常に特殊なエラーが発生することはないと考えられます。
使用するコマンドをさらに理解するには、コマンドプロンプトウィンドウを開き、そこで次のコマンドを実行し、各コマンドに表示されるヘルプを非常に注意深く読んでください。
Windowsバッチファイルを使用して複数のコマンドを含む1行で、ここ&&
で&
使用される演算子について説明します。
次は、私たちがコマンドを使用して、バッチファイルソリューションに見てみましょうDELを内のファイルを削除する%PathToFolder%
と、FORとRDの中にサブフォルダを削除します%PathToFolder%
。
@echo off
setlocal EnableExtensions DisableDelayedExpansion
rem Clean the folder for temporary files if environment variable
rem PathToFolder is not defined already outside this batch file.
if not defined PathToFolder set "PathToFolder=%TEMP%"
rem Remove all double quotes from folder path.
set "PathToFolder=%PathToFolder:"=%"
rem Consisted the folder path only of double quotes?
if not defined PathToFolder goto EndCleanFolder
rem Remove a backslash at end of folder path.
if "%PathToFolder:~-1%" == "\" set "PathToFolder=%PathToFolder:~0,-1%"
rem Consisted folder path only of a backslash (with one or more double quotes)?
if not defined PathToFolder goto EndCleanFolder
rem Delete all files in specified folder including files with hidden
rem or read-only attribute set, except the files currently opened by
rem a running process which prevents deletion of the file while being
rem opened by the application, or on which the current user has not
rem the required permissions to delete the file.
del /A /F /Q "%PathToFolder%\*" >nul 2>nul
rem Delete all subfolders in specified folder including those with hidden
rem attribute set recursive with all files and subfolders, except folders
rem being the current directory of any running process which prevents the
rem deletion of the folder and all folders above, folders containing a file
rem opened by the application which prevents deletion of the file and the
rem entire folder structure to this file, or on which the current user has
rem not the required permissions to delete a folder or file in folder tree
rem to delete.
for /F "eol=| delims=" %%I in ('dir "%PathToFolder%\*" /AD /B 2^>nul') do rd /Q /S "%PathToFolder%\%%I" 2>nul
:EndCleanFolder
endlocal
バッチファイルは、最初に、PathToFolder
二重引用符のないフォルダーパスと最後にバックスラッシュのない環境変数が実際に定義されていることを確認します。最後のバックスラッシュは問題にはなりませんが、PathToFolder
バッチファイルの実行中にの値が他の文字列と連結されるため、フォルダーパスの二重引用符は問題になる可能性があります。
重要なのは次の2行です。
del /A /F /Q "%PathToFolder%\*" >nul 2>nul
for /F "eol=| delims=" %%I in ('dir "%PathToFolder%\*" /AD /B 2^>nul') do rd /Q /S "%PathToFolder%\%%I" 2>nul
コマンドDELは、指定されたディレクトリ内のすべてのファイルを削除するために使用されます。
- オプション
/A
は、DELがオプションを使用せずに無視する隠し属性を持つファイルを含む実際にすべてのファイルを処理するために必要/A
です。
- このオプション
/F
は、読み取り専用属性が設定されているファイルを強制的に削除するために必要です。
- このオプション
/Q
は、複数のファイルを本当に削除する必要がある場合に、ユーザーにプロンプトを表示せずに複数のファイルを静かに削除するために必要です。
>nul
STDOUTを処理するために記述されたファイル名の出力を、ファイルが現在開かれているか、ユーザーがファイルを削除する権限を持っていないため削除できないデバイスNULにリダイレクトする必要があります。
2>nul
削除できない各ファイルのエラーメッセージ出力をハンドルSTDERRからデバイスNULにリダイレクトする必要があります。
コマンドFORおよびRDは、指定されたディレクトリー内のすべてのサブディレクトリーを削除するために使用されます。ただし、この場合for /D
、FORは非表示の属性が設定されたサブディレクトリを無視するため、使用されません。そのため、for /F
を使用してバックグラウンドで開始された別のコマンドプロセスで次のコマンドラインを実行します%ComSpec% /c
。
dir "%PathToFolder%\*" /AD /B 2>nul
dirは/B
、attributeのあるディレクトリエントリD
、つまり、パスのない隠し属性のような他の属性に依存しない、指定されたディレクトリ内のすべてのサブディレクトリの名前のため、ベアフォーマットで出力します。ハンドルSTDERRからディレクトリが見つからない2>nul
場合にDIRが出力するエラーメッセージをデバイスNULにリダイレクトするために使用されます。
リダイレクト演算子には>
、キャレット文字でエスケープする必要があります^
に、FORの Windowsコマンド・インタプリタは、コマンドを実行する前に、このコマンドラインを処理するときにリテラル文字として解釈されるコマンドラインFOR埋め込ま実行するdir
開始した別のコマンド・プロセスにコマンドラインをバックグラウンドで。
FORは、開始されたコマンドプロセスのSTDOUTを処理するために書き込まれたキャプチャされた出力を処理します。これは、パスなしのサブディレクトリの名前であり、二重引用符で囲まれていません。
オプション付きのFORは、オプション付きのDIRが空行を出力/F
しないため、ここでは発生しない空行を無視します。/B
FORは、デフォルトの行末文字であるセミコロンで始まる行も無視します。ディレクトリ名はセミコロンで始めることができます。そのためeol=|
、縦棒文字を行末文字として定義するために使用されます。これは、ディレクトリまたはファイルがその名前に持つことはできません。
FORは、スペースと水平タブを区切り文字として使用して行を部分文字列に分割し、最初のスペース/タブ区切りの文字列のみを指定されたループ変数に割り当てますI
。ディレクトリ名には1つ以上のスペースを含めることができるため、この分割動作はここでは不要です。したがってdelims=
、区切り記号の空のリストを定義して、行分割動作を無効にし、ループ変数に割り当てられます。これはI
、常に完全なディレクトリ名です。
コマンドFORは、パスなしで各ディレクトリ名に対してコマンドRDを実行します。これが、RDコマンドラインでフォルダーパスをもう一度指定する必要がある理由であり、サブフォルダー名と連結されます。
使用するコマンドとその機能を理解するには、コマンドプロンプトウィンドウを開いて次のコマンドを実行し、各コマンドに対して表示されるすべてのヘルプページをよく読みます。
del /?
dir /?
echo /?
endlocal /?
for /?
goto /?
if /?
rd /?
rem /?
set /?
setlocal /?