我試圖向用戶展示正確的下載速度,但我的應用程式下載同時是一堆小檔案,為了加快我正在使用的速度Parallel.ForEach。但是我無法計算正確的下載速度。使用我當前的代碼,我基本上是在計算平均下載速度,而不是當前下載的速度。因為每次下載完成時它都會更新 UI。當我使用正常時foreach,我可以正確計算,但速度很慢。如何使用多個執行緒和多個檔案正確顯示下載的 Mbps?
注意:這個應用程式是 WPF,但我幾乎沒有使用任何 MVVM。這是我第一次使用 WPF,目前我只是在嘗試制作具有良好功能的好看的東西。
下載功能
var stopwatch = new Stopwatch();
stopwatch.Start();
DownloadController.stopwatch.Start();
DownloadController.IsDownloadStarted = true;
DownloadController.IsDownloadInProgress = true;
Parallel.ForEach(downloadList, new ParallelOptions { MaxDegreeOfParallelism = 5 }, file =>
{
try
{
DownloadController.LastDownloadingFileName = file.FileName;
GET_DownloadFile(file.FileName, file.LastUpdate.UnixTimeStampToDateTime()).GetAwaiter().GetResult();
logger.Info("Download", file.FileName, "Downloading file completed");
}
catch (Exception ex)
{
lock (_failedDownloads)
{
_failedDownloads.Add(file);
}
logger.Exception(ex, "Download", file.FileName, file.LastUpdate, file.Size, $"Failed to download file");
}
});
進度改變事件
public static void DownloadProgressChangedEvent(object sender, DownloadProgressChangedEventArgs e)
{
MainWindow._dispatcher.BeginInvoke(new Action(() =>
{
ButtonProgressAssist.SetValue(MainWindow.This.Prog_Downloading, ProgressValue);
ButtonController.ButtonPlay_Downloading();
if (e.ProgressPercentage == 100)
{
DownloadedSize = e.TotalBytesToReceive;
var downloadSpeed = string.Format("{0} ", (DownloadedSize / 1024.0 / 1024.0 / stopwatch.Elapsed.TotalSeconds).ToString("0.0"));
var text1 = $"({ProgressValue}% - {DownloadedFileCount}/{TotalFileUpdateCount}) @ {downloadSpeed}MB/s {EasFile.GetFileNameWithExtension(LastDownloadingFileName)} ";
MainWindow.This.DownloadTextBlock.Text = text1;
}
}));
}
進度完成事件
public static void DownloadProgressCompletedEvent(object? sender, AsyncCompletedEventArgs e)
{
if (!e.Cancelled)
{
DownloadedFileCount ;
}
}
我試圖用來PerformanceCounter查看我當前應用程式的網路使用情況,但它只顯示特定網路上所有使用情況的使用情況。
uj5u.com熱心網友回復:
您在這里有兩個選擇:第一種方法是創建一個處理單個檔案下載的類。在這個類中,您應該計算下載的位元組數。一種可能的解決方案是讓一個成員每秒被清除一次。應將接收到的位元組添加到其中。在清除之前,該類應該將該值報告給它應該成為成員的主類,對所有當前下載的檔案以相同的方式進行操作。另一種解決方案不是在每個進度事件上都有一個類來報告接收到的位元組和時間。在主類中,您應該有一個存盤這些對的串列。然后每一秒你只能得到最后一秒的記錄并聚合接收到的位元組。
PS 訪問成員應該是執行緒安全的兩種方式。
轉載請註明出處,本文鏈接:https://www.uj5u.com/ruanti/527031.html
標籤:C#。网wpf
