Modify ZipEntry.FileName in foreach loop not working

Feb 26, 2010 at 4:07 PM


I try to modify  ZipEntry.FileName inside a Foreach loop but it's not working as the original Zip entry is modifying and the loop is broken

here is my code (get from dotnetziplib sample):

foreach (ZipEntry entry in zip)
     if (entry.FileName.EndsWith(".rtf"))
          var newname = "renamed_files\\" + entry.FileName;

          entry.FileName = newname;
          entry.Comment = "renamed";                                                
I get the following error:
"Collection was modified; enumeration operation may not execute."
Do you have any idea How I can do that ?


Feb 26, 2010 at 6:12 PM

Yes, try this.....

foreach (ZipEntry entry in zip.EntriesSorted)

I tried your code and got the same error.  I think that it's unfortunate that the error occurs.  I'll have to look into removing it.

Feb 26, 2010 at 6:17 PM
Edited Feb 26, 2010 at 6:27 PM

The problem is that internally the set of entries is stored as a Dictionary<String,ZipEntry>.  The string is the entry name.  This allows quick access using the string indexer. 

Renaming an entry - setting the FileName on the entry -  causes the entry to be removed and then re-added into the Dictionary. This modifies the collection and prevents the foreach from continuing.

You have the workaround I have to you.  Another possible workaround is to copy the list of entries and enumerate through the copy.

A possible solution is for DotNetZip to return a copy of the List for the foreach loop.  With the fix you could do "foreach(var entry in zip) ..." and get the expected results, even if you rename an entry within the loop.  The problem is that for large zip files, doing a copy for a foreach loop that does not involve renaming any entries, would be unnecessarily slow, and memory hungry.  So at this point I'm not sure I want to make the change.

For now I am leaning toward making a document change that describes this limitation and the workarounds.



Feb 26, 2010 at 6:41 PM
This discussion has been copied to a work item. Click here to go to the work item and continue the discussion.