Making this VBScript decision :
$zipfile = 'C:\path\to\your.zip' $files = 'some.file', 'other.file', ... $dst = 'C:\some\folder' $app = New-Object -COM 'Shell.Application' $app.NameSpace($zipfile).Items() | ? { $files -contains $_.Name } | % { $app.Namespace($dst).MoveHere($_) Remove-Item (Join-Path $dst $_.Name) }
If you have .net Framework 4.5 installed, then something like this should work too:
[Reflection.Assembly]::LoadWithPartialName('System.IO.Compression') $zipfile = 'C:\path\to\your.zip' $files = 'some.file', 'other.file', ... $stream = New-Object IO.FileStream($zipfile, [IO.FileMode]::Open) $mode = [IO.Compression.ZipArchiveMode]::Update $zip = New-Object IO.Compression.ZipArchive($stream, $mode) ($zip.Entries | ? { $files -contains $_.Name }) | % { $_.Delete() } $zip.Dispose() $stream.Close() $stream.Dispose()
Brackets around filtering items from the Entries collection are required, because otherwise the subsequent Delete() will modify the collection. This will prevent the reading (and therefore removal) of other items from the collection. The resulting error message is as follows:
An error occurred while enumerating through a collection: Collection was modified;
enumeration operation may not execute ..
At line: 1 char: 1
+ $ zip.Entries | ? {$ filesToRemove -contains $ _. Name} | % {$ _. Delete ()}
+ ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ ~~~~~~~~~~~~~~~~~~~~~~~~~~
+ CategoryInfo: InvalidOperation: (System.Collecti ... ipArchiveEntry]: Enumerator) [], RuntimeException
+ FullyQualifiedErrorId: BadEnumeration source share