正确计算文件副本的剩余时间

时间:2016-04-30 14:46:15

标签: vb.net

我有问题正确估计一个现实的剩余时间'应用程序的副本应用程序。我使用Filestream作为副本,因为要复制的文件从> 1MB到4GB不等。我在这里使用percentageTotal来计算文件复制的当前位置:

  'Loop through each file in the SourceDir
            For Each ChildFile In SourceDir.GetFiles()

                If (worker.CancellationPending = True) Then
                    e.Cancel = True
                End If

                'Calculate data being moved for eta to completion
                Dim filetotalbytes As Double = ChildFile.Length
                filetotalsofarcopied = filetotalbytes + filetotalsofarcopied


                'Display file being copied
                SetLabelText_ThreadSafe(Me.lblStatus, "Copying: " & line & "\" & ChildFile.Name & "")

                'Do the copy
                ChildFile.CopyTo(Path.Combine(DestDir.FullName, ChildFile.Name), True)

                'Contruct Destination and Source Strings
                deststring = DestDir.ToString & "\" & ChildFile.Name
                Dim sourcedirstring As String
                sourcedirstring = SourceDir.ToString & "\" & ChildFile.Name

        Dim CopyStream As New FileStream(sourcedirstring, FileMode.Open, FileAccess.Read)
        Dim NewStream As New FileStream(deststring, FileMode.Append)

        Dim Buffer(4096) As Byte
        Dim BytesRead As Integer
        Dim len As Long = CopyStream.Length - 1

        While CopyStream.Position < len


            BytesRead = CopyStream.Read(Buffer, 0, Buffer.Length)
            NewStream.Write(Buffer, 0, BytesRead)

            percentageTotal = ((NewStream.Length + filetotalsofarcopied) / Overallsize * 100)
            percentageTotal = Decimal.Round(percentageTotal)

            '  SetLabelText_ThreadSafe(Me.lblTotalProgress, "" & percentageTotal & "%")

        End While

        CopyStream.Dispose()
        NewStream.Dispose()

我发现percentageTotal的值经常跳跃而不是像我期望的那样以线性方式增加。谁能看到我在哪里错了?

此外,我无法完善secondsremaining值的逻辑。它目前显示复制花费的天数,最初运行之前快速减少,但显然不是正确的剩余时间。

 'Start process snippit
 'Start Button Click config - starts the backgroundworker
Public Sub Button1_Click(sender As Object, e As EventArgs) Handles Button1.Click

   'Set start value - label22 is hidden on form1
    Label22.Text = "0"

    'Start timers
    Timer3.Start()
    Timer4.Start()


    'Start background worker
    BackgroundWorker1.WorkerSupportsCancellation = True
    BackgroundWorker1.WorkerReportsProgress = True
    BackgroundWorker1.RunWorkerAsync()

End Sub

UPDATED!并且表单末尾的Timer.Tick代码计算剩余时间:

 Private Sub Timer1_Tick(sender As Object, e As EventArgs) Handles Timer1.Tick
    byteslastsecond = filetotalsofarcopied
End Sub


'Every tick of Timer4 calculates the time needed to complete the copy.
   Private Sub Timer4_Tick(sender As Object, e As EventArgs) Handles Timer4.Tick
    Dim time As Long = Label22.Text
    If percentageTotal = 0 Then
        SetLabelText_ThreadSafe(Me.lblEstTimeLeft, "Estimated Time Left (All Files): Estimating...")
    Else
         Dim secondsRemaining As Double = (Overallsize - filetotalsofarcopied) / (filetotalsofarcopied - byteslastsecond)
        Dim ts As TimeSpan = TimeSpan.FromSeconds(secondsRemaining)

任何人都可以在剩下的时间内纠正我的逻辑吗?

1 个答案:

答案 0 :(得分:1)

代码的问题在于,即使整个文件尚未复制,您也会将filetotalsofarcopied增加整个文件大小。您应该在复制数据块时递增它。

所以删除它:

'Calculate data being moved for eta to completion
Dim filetotalbytes As Double = ChildFile.Length
filetotalsofarcopied = filetotalbytes + filetotalsofarcopied

并将其放入While循环中:

BytesRead = CopyStream.Read(Buffer, 0, Buffer.Length)
NewStream.Write(Buffer, 0, BytesRead)

filetotalsofarcopied += BytesRead

percentageTotal = ((NewStream.Length + filetotalsofarcopied) / Overallsize * 100)
percentageTotal = Decimal.Round(percentageTotal)

这应该使时间估计工作正确,并显示百分比。

您还应删除此内容:

'Do the copy
ChildFile.CopyTo(Path.Combine(DestDir.FullName, ChildFile.Name), True)

因为你通过两次复制文件浪费时间和资源。

修改

实际上,我错过了一些错误。

此:

percentageTotal = ((NewStream.Length + filetotalsofarcopied) / Overallsize * 100)

应该是这样的:

percentageTotal = (filetotalsofarcopied / Overallsize * 100)

因为当前的写入字节数已经通过filetotalsofarcopied变量添加到BytesRead