【发布时间】:2017-05-07 11:17:41
【问题描述】:
我正在实施一种通信算法,以定期且非常快速地发送信息,即包之间的 1 毫秒。我有一个使用任务发送包的功能版本。这是我的代码示例:
private void Work()
{
Stopwatch stopwatch = new Stopwatch();
stopwatch.Start();
while (!cancellationTokenSource.Token.IsCancellationRequested)
{
if (!Pack.PeriodicOn)
cancellationTokenSource.Cancel();
// Time used to send the packs before the interval time
double tolerance = Pack.Interval * 0.2F;
// In case of interval bigger than 25ms send pasks only 5ms before
if (tolerance > 5) tolerance = 5;
TimeSpan timeSpan = stopwatch.Elapsed;
// The waiting time is controlled by the condition below, if the condition is false, the while loop continues execution
// Send the information a little bit before to interval time to deal with the transmision delay
if (Pack.LastSent.TotalMilliseconds == 0 ||
timeSpan.TotalMilliseconds - Pack.LastSent.TotalMilliseconds >=
(Pack.Interval - tolerance))
{
SendData(Pack);
Pack.LastSent = timeSpan;
}
}
Pack.LastSent = new TimeSpan(0);
}
我的问题在于 CPU 使用率增加到不理想的水平。我知道我可以通过引入一些延迟来避免这种情况,但是, Thread.Sleep(1) 非常不准确,包之间的实际传输间隔增加,如果我使用 await Task.Delay(1) 似乎会产生相同的效果。
有没有人有替代方法来准确地引入任务延迟?
提前致谢!
【问题讨论】:
-
Windows 不是实时操作系统:/
-
其他 SO 答案,例如stackoverflow.com/questions/6254703/… 似乎在说旋转 CPU,就像你正在做的那样,是要走的路。
-
理解您所说的“非常不准确”会有所帮助。你看到多少变化?你系统的定时器间隔是多少(默认是15ms)
-
您可以通过插入“Thread.Sleep(Pack.Interval-(timeSpan.TotalMilliseconds - Pack.LastSent.TotalMilliseconds))”作为 while 循环的最后一条指令来等待适当的睡眠延迟。跨度>
-
我正在尝试尽可能地减小方差...很确定 Thread.Slep(x) 不会解决问题,即使 x 大于 15 它也无法完成延迟差异很小,这就是我要问的原因:)
标签: c# .net multithreading winforms task