2009-11-09 93 views
4

我已经实现了一个文件传输速率计算器,以显示在我的应用程序中发生的上传过程的kB /秒,但使用以下代码,似乎我在我的KB/s读数中获得“突发”文件开始上传后。计算上传传输速度问题

这是我的流的代码的部分中,此流在1024块到服务器中使用的HttpWebRequest一个文件:

using (Stream httpWebRequestStream = httpWebRequest.GetRequestStream()) 
{ 
    if (request.DataStream != null) 
    { 
     byte[] buffer = new byte[1024]; 
     int bytesRead = 0; 

     Debug.WriteLine("File Start"); 
     var duration = new Stopwatch(); 
     duration.Start(); 
     while (true) 
     { 
      bytesRead = request.DataStream.Read(buffer, 0, buffer.Length); 
      if (bytesRead == 0) 
       break; 

      httpWebRequestStream.Write(buffer, 0, bytesRead); 
      totalBytes += bytesRead; 


      double bytesPerSecond = 0; 
      if (duration.Elapsed.TotalSeconds > 0) 
       bytesPerSecond = (totalBytes/duration.Elapsed.TotalSeconds); 

      Debug.WriteLine(((long)bytesPerSecond).FormatAsFileSize()); 
     } 
     duration.Stop(); 
     Debug.WriteLine("File End"); 
     request.DataStream.Close(); 
    } 
} 

现在上传过程的输出日志和相关联的Kb /秒读数如下: (你会注意到一个新的文件开始,用“文件开始”和“文件结束”结束)

File Start 
5.19 MB 
7.89 MB 
9.35 MB 
11.12 MB 
12.2 MB 
13.13 MB 
13.84 MB 
14.42 MB 
41.97 kB 
37.44 kB 
41.17 kB 
37.68 kB 
40.81 kB 
40.21 kB 
33.8 kB 
34.68 kB 
33.34 kB 
35.3 kB 
33.92 kB 
35.7 kB 
34.36 kB 
35.99 kB 
34.7 kB 
34.85 kB 
File End 

File Start 
11.32 MB 
14.7 MB 
15.98 MB 
17.82 MB 
18.02 MB 
18.88 MB 
18.93 MB 
19.44 MB 
40.76 kB 
36.53 kB 
40.17 kB 
36.99 kB 
40.07 kB 
37.27 kB 
39.92 kB 
37.44 kB 
39.77 kB 
36.49 kB 
34.81 kB 
36.63 kB 
35.15 kB 
36.82 kB 
35.51 kB 
37.04 kB 
35.71 kB 
37.13 kB 
34.66 kB 
33.6 kB 
34.8 kB 
33.96 kB 
35.09 kB 
34.1 kB 
35.17 kB 
34.34 kB 
35.35 kB 
34.28 kB 
File End 

我的问题是,你会发现,在“爆”我一开始讲的开始的每个新文件,在峰值达到峰值,然后平衡正常。这样的上传是否正常?我的上传速度通常不会高于40k /秒,所以它不可能是正确的。

这是一个真正的问题,当我平均进行屏幕显示的最后5到10秒时,它真的会抛出一些结果产生大约〜3MB/sec的结果!

任何想法,如果我接近这个问题的最佳途径?我该怎么办? :S

格雷厄姆

另外:为什么我不能做 'bytesPerSecond = (bytesRead/duration.Elapsed.TotalSeconds)' 和移动duration.Start & duration.Stop到while循环和接收准确的结果?我会认为这会更准确?每个速度读数为900字节/秒,800字节/秒等。

回答

3

我这样做的方式是: 保存长传输的所有字节。

然后每隔1秒我检查一下已转移了多少。所以我基本上只触发代码,以节省一秒钟的速度。您的while循环将在快速网络中一秒钟循环maaaaaaaaaaaany次。

根据网络的速度,您可能需要检查在单独的线程或函数中传输的字节。我喜欢用定时器做这件事,所以我可以很容易地更新UI

编辑: 从你看你的代码,即时猜测你做错了什么,你不考虑while(true)中的一个循环是不是1秒

编辑2: 另一个只做速度检查的优点是事情会变得更快。在这种情况下,更新UI可能是你做的最慢的事情,所以如果你试图在每个循环中更新UI,那很可能是你的最慢点,并且会产生没有反应的UI。

你也正确,你应该avarage的价值观,所以你没有得到microsoft minutes错误。我normaly做的定时器功能运行做这样的事情:

//Global variables 
long gTotalDownloadedBytes; 
long gCurrentDownloaded; // Where you add up from the download/upload untill the speedcheck is done. 
int gTotalDownloadSpeedChecks; 


//Inside function that does speedcheck  
gTotalDownloadedBytes += gCurrentDownloaded; 
gTotalDownloadSpeedChecks++; 

long AvgDwnSpeed = gTotalDownloadedBytes/gTotalDownloadSpeedChecks; // Assumes 1 speedcheck pr second. 
+0

感谢,以及循环不走高速每1024块,但这也是顺利更新进度条,这一切工作,并一直没有问题。我认为我已经通过调整我的平均值来等待一秒钟来解释我的问题,但是仍然不确定为什么会这样爆发。 – GONeale 2009-11-09 12:28:19

+0

增加了EDIT2。解释更多 – EKS 2009-11-09 12:32:16

+0

感谢EKS,你最大的帮助了我,我会看看我是否可以在以后进行优化。 – GONeale 2009-12-21 23:34:19

0

好,我想我已经通过调整5个固定我的问题 - 10 averging变量等待一秒钟,占爆裂,不最好的,但将允许互联网自我排序,并允许我捕捉顺利转移。

它从我的网络流量下来的权利是爆破出现这样是没有在代码中,我可以做不同,以阻止这一切。

在我犹豫地接受我自己的答案之前,请您仍然对更多答案感兴趣。

2

有你和你发送到系统软件和硬件之间多层次,和一些这些层具有缓冲空间一定量可用。

当你第一次开始发送,您可以相当迅速泵出的数据,直到你填补这些缓冲器 - 这不是真正让所有的方式向另一端那么快,但!在填充发送缓冲区后,您只能将相同速率的更多数据放入发送缓冲区,因此您看到的速率将降至基础网络发送速率。您的评论