Каждый раз, когда вы Invoke
, есть задержка и стоимость, так как мы должны отправить сообщение в поток пользовательского интерфейса, по сути, это сообщение «пожалуйста, запустите этот код». Затем мы должны подождать, пока поток пользовательского интерфейса заберет это сообщение (в настоящее время он может быть занят выполнением какой-то другой работы), выполнить код, который мы его просили, и показать, что это сделано. Затем, наконец, мы можем возобновить работу после вызова Invoke
.
Теперь, по большому счету, эта стоимость довольно низкая. Так что, если вы просто используете Invoke
один или два раза, это не стоит рассматривать. Однако, если вы планируете выполнить большой цикл и Invoke
внутри цикла, вы можете сделать паузу и пересмотреть. Вместо этого лучше переместить Invoke
за пределы цикла.
Однако поток пользовательского интерфейса является ценным ресурсом. Мы не хотим тратить время на этот поток, выполняя не задачи, связанные с пользовательским интерфейсом.
Так что, если у вас есть цикл, выполняющий смесь работы с интенсивным использованием процессора и обновлений пользовательского интерфейса, ни один из них не обязательно подходит. В таком случае, посмотрите, можете ли вы реструктурировать свой код так, чтобы вы готовили пакетов обновлений пользовательского интерфейса в цикле, а затем время от времени (или после цикла, если это возможно) выполняли Invoke
, чтобы просто выполнить эти обновления пользовательского интерфейса.
В вашем случае, похоже, у вас уже есть пакет обновлений пользовательского интерфейса для выполнения. Поэтому предпочтите код, который Invoke
один раз, чтобы сделать все три:
if (mainForm.InvokeRequired)
{
mainForm.Invoke(
(Action)(() =>
{
mainForm.label1.Text = "update";
mainForm.textBox1.Text = "update";
mainForm.button1.Text = "update";
}));
}
else
{
mainForm.label1.Text = "update";
mainForm.textBox1.Text = "update";
mainForm.button1.Text = "update";
}
Но учтите, что обычно лучше структурировать код так, чтобы вы не дублировали фактических обновлений пользовательского интерфейса, которые у вас есть выше. Что-то вроде:
private void DoUpdate()
{
if(mainForm.InvokeRequired)
{
mainForm.Invoke(DoUpdate);
return;
}
mainForm.label1.Text = "update";
mainForm.textBox1.Text = "update";
mainForm.button1.Text = "update";
}