У мене є сценарій. (Форми Windows, C #, .NET)
- Існує основна форма, в якій розміщено деякий контроль користувачів.
- Управління користувачем виконує деякі важкі операції з даними, так що якщо я безпосередньо викликаю
UserControl_Load
метод, інтерфейс користувача не відповідає на тривалість виконання методу навантаження. - Щоб подолати це, я завантажую дані на різні потоки (намагаюся змінити існуючий код якомога менше)
- Я використовував фоновий робочий потік, який буде завантажувати дані, і коли це завершиться, сповістить програму, що вона виконала свою роботу.
- Тепер виникла справжня проблема. Весь інтерфейс користувача (основна форма та його дочірні користувальницькі контролі) був створений на основній основній темі. У методі LOAD користувачаcontcontrol я отримую дані на основі значень деякого контролю (наприклад, текстового поля) на userControl.
Псевдокод виглядатиме так:
КОД 1
UserContrl1_LoadDataMethod()
{
if (textbox1.text == "MyName") // This gives exception
{
//Load data corresponding to "MyName".
//Populate a globale variable List<string> which will be binded to grid at some later stage.
}
}
Виняток, який він дав, був
Операція перехресних потоків не вірна: керування доступ здійснюється з потоку, відмінного від потоку, на якому він створений.
Щоб дізнатись більше про це, я зробив деякий гуглінг, і з’явилася пропозиція, якби використати наступний код
КОД 2
UserContrl1_LoadDataMethod()
{
if (InvokeRequired) // Line #1
{
this.Invoke(new MethodInvoker(UserContrl1_LoadDataMethod));
return;
}
if (textbox1.text == "MyName") // Now it wont give an exception
{
//Load data correspondin to "MyName"
//Populate a globale variable List<string> which will be binded to grid at some later stage
}
}
АЛЕ АЛЕ, АЛЕ ... здається, я повернувся до квадратного. Додаток знову стає безвідповідальним. Здається, це пов'язано із виконанням рядка №1, якщо це умова. Завдання з завантаження знову виконується батьківською ниткою, а не третьою, яку я породив.
Я не знаю, сприйняв я це правильно чи неправильно. Я новачок у нитці.
Як я вирішую це, а також який ефект від виконання рядка №1, якщо блокувати?
Ситуація така : я хочу завантажити дані в глобальну змінну на основі значення елемента керування. Я не хочу змінювати значення контролю з дочірньої нитки. Я не збираюся робити це ніколи з дитячої нитки.
Отже, лише доступ до значення, щоб відповідні дані можна було отримати з бази даних.