Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Foreach loop on windows command line?

I have a command line which copies files from folder A to folder B:

copy A\* B\

I would now like to delete all files in B that are present in A, non-recursively. I can list the files in A like this:

dir /b /a-d A

With the output being:

f0.txt
f1.txt
f2.txt

Here is the pseudocode for what I would like to do:

foreach $1 in <dir /b /a-d A output>:
  del B\$1

Is there a windows command-line syntax that will execute a command, using the output of another command as an input? I am aware of the piping operator ( | ) but do not know of a way that this could be used to accomplish this task. Any help would be appreciate.

Restriction: Only commands available by default in Windows 7.

like image 702
Adam S Avatar asked Jan 28 '12 17:01

Adam S


People also ask

How do I run a loop in CMD?

Related commands:FOR /R - Loop through files (recurse subfolders) . FOR /D - Loop through several folders. FOR /L - Loop through a range of numbers. FOR /F - Loop through items in a text file.

What does %1 do in CMD?

When used in a command line, script, or batch file, %1 is used to represent a variable or matched string. For example, in a Microsoft batch file, %1 can print what is entered after the batch file name.

How do I follow a path in CMD?

Go to the destination folder and click on the path (highlights in blue). type cmd. Command prompt opens with the path set to your current folder.


1 Answers

You can iterate over files with

for %x in (*) do ...

which is also a lot more robust than trying to iterate over the output of a command for this use case.

So

for %f in (A\*) do del "B\%~nxf"

or, if you need this in a batch file instead of the command line:

for %%f in (A\*) do del "B\%%~nxf"

%~nxf returns only the file name and extension of each file since it will be prefixed with A\ and you want to delete it in B.

Add > nul 2>&1 to suppress any output (error messages may appear when you try deleting files that don't exist).


Just for completeness, you can in fact iterate over the output of a command in almost the same way:

for /f %x in ('some command') do ...

but there are several problems with doing this and in the case of iterating over dir output it's rarely necessary, hence I don't recommend it.


And since you are on Windows 7, you have PowerShell as well:

Get-ChildItem A\* | ForEach-Object { Remove-Item ('B\' + $_.Name) }

or shorter:

ls A\* | % { rm B\$($_.Name) }
like image 66
Joey Avatar answered Sep 30 '22 14:09

Joey