我正在编写一个使用串行端口对数据进行采样的程序。我尝试实现的是一个等待“循环”,我可以等待几分钟,然后从串口获取数据。但是,在等待时,我以2Hz的速率从另一个串口获取数据,这是通过timer_Elapsed事件完成的。
我的问题是,作为c#中的新程序员,我不知道如何实现一个好的,可靠的等待方法。这是必需的,因为在等待下一个数据样本时我不希望执行任何操作(除了事件)。我一直在关注的是;
private async void wait(int time)
{
var delay = Task.Run(async () =>
{
Stopwatch sw = Stopwatch.StartNew();
await Task.Delay(time);
sw.Stop();
return sw.ElapsedMilliseconds;
});
Debug.Write("Millisecs", delay.Result.ToString());
}
效果不佳,因为它是非阻塞的,并且不知何故会混淆串行通信。
System.Threading.Thread.Sleep(120000);
冻结每一个
这似乎对我没什么好处,因为我仍然需要冻结主线程才能运行另一个,使得timer_Elapsed - 事件很难正确处理。
可悲的是,无法写出任何更好的内容,我会遵循以下内容;
while (ticks < 150)
{
Application.DoEvents();
}
(int ticks是timer_Elapsed事件的计数)
根据任务经理的说法,迫使我禁用大多数UI按钮,表单本身也让我非常紧张,同时只占用了大约50%的CPU容量。我只需要建议哪种编码方法适合我的场景类型。
感谢您的时间!
编辑:
我只使用一个表单作为我的UI运行WinForm应用程序。整个代码是一场噩梦,我不会在这里发布。
经过几次尝试后,代码为我做了;
public async Void myMethod()
{
await Task.Delay(2000);
doStuff();
}
这真的很简单,上次我尝试这种方法时,我不知道出了什么问题。
答案 0 :(得分:0)
您可以更改“主线程”以对定时器事件执行操作。然后,如果阻塞任务正在运行,您可以添加逻辑以禁用这些计时器事件。然后,更改按钮,以便不直接触发任务,而是更新全局变量或添加到队列中所需的操作。
使用表单计时器的非常基本的示例:
public Action NextAction;
public bool Running;
private void MainForm_Load(object sender, EventArgs e)
{
timer1.Tick += timer1_Tick;
timer1.Interval = 5000;
timer1.Start();
}
void timer1_Tick(object sender, EventArgs e)
{
if (!Running && NextAction != null)
{
Running = true;
NextAction();
Running = false;
}
}
void button1_Click(object sender, EventArgs e)
{
NextAction = () => TaskMethod();
}
void TaskMethod()
{
// do something
}