【问题标题】:WinZip, VB.Net Command Line max size of zip fileWinZip, VB.Net 命令行 zip 文件的最大大小
【发布时间】:2015-02-26 10:45:54
【问题描述】:

我需要有关 WinZip 命令行的帮助。 我目前有一个命令行可以正常工作,但如果文件夹超过 4GB,则会崩溃。我有超过 100MB 的非常大的 Tiffs 文件。我想在文件达到 2GB 时对其进行拆分。

这是我的代码

Private Sub btnStart_Click(sender As Object, e As EventArgs) Handles btnStart.Click
        deleteCount = 0
        Dim i, x As Integer
        Dim reNamedTo As String
        Dim newFileURL, newFolderURL As String
        Dim folderInfo As New System.Text.StringBuilder()

        Dim processedNumberCount As Integer = 0
        Dim numberOfErrors As Integer = 0
        Dim fileSucessfullyDone As Integer
        '  cboPattern.SelectedIndex = 0
        btnList_Click(sender, e)

        For i = 0 To ListBoxFoldersToBeDone.Items.Count - 1
            newFolderURL = ListBoxFoldersToBeDone.Items(i).ToString
            Try
                'must download winZip command line 32 / 64 bit depending on the verion of winZip u have
                Dim dirInfo As New System.IO.DirectoryInfo(newFolderURL)
                Dim folderName As String = (dirInfo.Name)
                reNamedTo = newFolderURL & "\" & folderName & ".zip"


                lblFolderBeingDone.Text = reNamedTo
                psiProcess.FileName = "C:\Program Files\Winzip\wzzip.exe"
                psiProcess.WorkingDirectory = newFolderURL
                psiProcess.WindowStyle = ProcessWindowStyle.Minimized
                psiProcess.ErrorDialog = False
                psiProcess.CreateNoWindow = True
                '  psiProcess.Arguments = ("" & " -a -p -r -m """ & reNamedTo & """ *.tif")
                psiProcess.Arguments = ("" & " -a -p -r """ & reNamedTo & """ *.tif")

                udtProc = Process.Start(psiProcess)
                udtProc.WaitForExit()
                'lblDeletingFiles.Text = reNamedTo
                processedNumberCount = processedNumberCount + 1
                lblCountItemsDone.Text = processedNumberCount.ToString
                pBar1.Value = processedNumberCount
                initStatusBar(processedNumberCount)
                listBoxFoldersDone.Items.Add(reNamedTo)
                deleteAfterZip(newFolderURL)
            Catch ex As Exception
                numberOfErrors = numberOfErrors + 1
                listBoxErrorFolders.Items.Add(reNamedTo)
            End Try
        Next

        udtProc.Close()
        listBoxFiles.Items.Clear()
        Dim title As String = "TIFF Files Zip Completed"
        Dim msg As String = "Process Complete , " & processedNumberCount & " files processed successfully.  " & numberOfErrors.ToString & " error(s) encountered"
        MessageBox.Show(msg, title)
        lblFolderBeingDone.Text = "-"

    End Sub

【问题讨论】:

  • 你在哪里声明psiprocess
  • 这是未经测试的,但对于 7-zip (7-zip.org),您可以使用 -v{size}[b|k|m|g](字节、千克、兆、千兆)选项;即 v2g 会将档案分成 2GB 的块。

标签: vb.net command-line filesize winzip


【解决方案1】:

您愿意接受完全不使用 WinZip 的不同解决方案吗? .Net 运行时实际上内置了压缩功能,最近的版本让我们更容易使用它。

要使下面的代码正常工作,您需要拥有 .Net 4.5,并且您需要在项目中添加对 System.IO.CompressionSystem.IO.Compression.FileSystem 的引用。它遍历给定的文件夹,将文件添加到 zip 文件,并在达到最大字节阈值后创建新的 zip 文件。这段代码唯一的缺点是最大字节阈值是根据未压缩文件长度计算的,因为压缩后的大小直到以后才知道。但是,根据您的要求,这应该是个问题。

代码的 cmets 应该可以解释一切。有两种方法,一种采用您不想压缩的可选文件扩展名数组。要使用代码使用 50MB 字节阈值将桌面压缩到“我的文档”文件夹中的文件夹,您只需执行以下操作:

Dim FolderToCompress = Environment.GetFolderPath(Environment.SpecialFolder.Desktop)
Dim FolderToSaveZipTo = Path.Combine(Environment.GetFolderPath(Environment.SpecialFolder.MyDocuments), "ZIPs")

CompressFolder(FolderToCompress, FolderToSaveZipTo, "MyArchive", 1024 * 1024 * 50)

这是代码:

''' <summary>
''' Compress a given folder splitting the zip files based on a supplied maximum uncompressed file length.
''' </summary>
''' <param name="folderToCompress">The folder to compress.</param>
''' <param name="folderToSaveZipFilesTo">The folder to save the compress files to.</param>
''' <param name="zipFileNameWithoutExtension">The file excluding the .zip extension to save to.</param>
''' <param name="maximumBytesToCompressPerFile">The maximum number of uncompress bytes that will be put into each zip file.</param>
''' <param name="fileExtensionsNotToCompress">An array of file extensions, including the leading period, to store only and not compress.</param>
Public Shared Sub CompressFolder(
                                    folderToCompress As String,
                                    folderToSaveZipFilesTo As String,
                                    zipFileNameWithoutExtension As String,
                                    maximumBytesToCompressPerFile As Long,
                                    fileExtensionsNotToCompress() As String
                                )
    ''Create the directory if it doesn't exist already
    Directory.CreateDirectory(folderToSaveZipFilesTo)

    ''Create a formattable string that increments an index each time
    Dim FileNameFormatForZip = zipFileNameWithoutExtension & "_{0}.zip"
    Dim CurrentZipFileIndex = 0

    ''The total amount of uncompressed files process so far
    Dim CurrentUncompressedBytesProcessedSoFar As Long = 0

    ''Objects that we'll init below
    Dim FileStreamForZip As Stream = Nothing
    Dim Zip As ZipArchive = Nothing

    ''Loop through each file in the given directory including all child directories
    For Each FI In Directory.EnumerateFiles(folderToCompress, "*.*", SearchOption.AllDirectories)

        ''Get the local file name relative to the parent directory
        Dim LocalName = FI.Replace(folderToCompress, "").TrimStart("\"c)

        ''If we don't currently have a stream created, create one
        If FileStreamForZip Is Nothing Then
            Dim FileToSaveZipTo = Path.Combine(folderToSaveZipFilesTo, String.Format(FileNameFormatForZip, CurrentZipFileIndex))
            FileStreamForZip = New FileStream(FileToSaveZipTo, FileMode.Create, FileAccess.Write, FileShare.None)

            Zip = New ZipArchive(FileStreamForZip, ZipArchiveMode.Create)
        End If

        ''Set a default compression level
        Dim CompressionLevel = System.IO.Compression.CompressionLevel.Optimal

        ''However, if the current file extension is on our do not compress list then only set it to store
        If fileExtensionsNotToCompress.Contains(New System.IO.FileInfo(FI).Extension) Then
            CompressionLevel = Compression.CompressionLevel.NoCompression
        End If

        ''Create our zip entry
        Dim ZE = Zip.CreateEntry(LocalName, CompressionLevel)

        ''Add our file's contents to the entry
        Using ZipStream = ZE.Open()
            Using FileStream = File.Open(FI, FileMode.Open, FileAccess.Read, FileShare.Read)
                FileStream.CopyTo(ZipStream)
            End Using
        End Using

        ''Increment our file byte counter by the uncompressed file's original size
        ''Unfortunately we can't use the ZE.CompressedLength because that is only available
        ''during the reading of a ZIP file
        CurrentUncompressedBytesProcessedSoFar += New System.IO.FileInfo(FI).Length

        ''If we're over the threshold for maximum bytes
        If CurrentUncompressedBytesProcessedSoFar >= maximumBytesToCompressPerFile Then

            ''Clean up and dispose of our objects
            Zip.Dispose()
            Zip = Nothing
            FileStreamForZip.Dispose()
            FileStreamForZip = Nothing

            ''Reset our counter
            CurrentUncompressedBytesProcessedSoFar = 0

            ''Increment the current file index
            CurrentZipFileIndex += 1
        End If
    Next

    ''Clean up
    If Zip IsNot Nothing Then
        Zip.Dispose()
        Zip = Nothing
    End If

    If FileStreamForZip IsNot Nothing Then
        FileStreamForZip.Dispose()
        FileStreamForZip = Nothing
    End If
End Sub

''' <summary>
''' Compress a given folder splitting the zip files based on a supplied maximum uncompressed file length.
''' </summary>
''' <param name="folderToCompress">The folder to compress.</param>
''' <param name="folderToSaveZipFilesTo">The folder to save the compress files to.</param>
''' <param name="zipFileNameWithoutExtension">The file excluding the .zip extension to save to.</param>
''' <param name="maximumBytesToCompressPerFile">The maximum number of uncompress bytes that will be put into each zip file.</param>
Public Shared Sub CompressFolder(folderToCompress As String, folderToSaveZipFilesTo As String, zipFileNameWithoutExtension As String, maximumBytesToCompressPerFile As Long )
    CompressFolder(folderToCompress, folderToSaveZipFilesTo, zipFileNameWithoutExtension, maximumBytesToCompressPerFile, {".zip", ".mp4", ".wmv"})

End Sub

【讨论】:

    猜你喜欢
    • 2020-11-19
    • 2015-05-09
    • 2015-01-27
    • 2012-08-21
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多