Коректне завершення потоків - stack overflow російською

Є клас потоку:

І оголошені в публічному розділі змінних форми три екземпляри таких:

Запуск потоку йде таким чином:

На подію Close форми ставлю такий код:







Він вивалює помилку пам'яті. Пробував так закривати разом з формою потік:

Пробував прописувати ще в подія destroy форми:

Але і це не допомагає ніяк. Помилки йдуть наполегливо, по причині того, що потік (і) некоректно закривається. Як перемогти цю помилку? Відразу кажу, що в потоці йде ще робота з базою даних, виведення даних на форму (лічильники і прогрес завантаження).

заданий 14 Серпня '15 о 14:56

Дякую за дійсно корисний відповідь! І все ж, судячи з того коду, що призвели на засланні, там все ж ADOConnection не створюється в класі потоку, він завантажує зовнішні дані від існуючого коннектора. Єдина відмінність від мого варіанту, що таблицю в коді там створюють внутрішню і її юзают, попередньо підключивши, компонент конектора. В іншому я робив також. - IntegralAL 15 Серпня '15 в 4:08







Не треба використовувати Resume. Цей метод, починаючи по-моєму з XE, пригнічений (deprecated). Всесто Resume використовуй Start. Але тільки в тому випадку, якщо потік створений Suspended, тобто викликаний перевантажених конструктор з передачею параметра CreateSuspended: = true

Не варто форсовано зупиняти вже запущений потік. Це викличе витік ресурсів (memory leaks). На виконання потоку можна лише вплинути. наприклад, повідомити його, що ти хочеш його перервати. Потік закінчиться тоді, коли виконається останній оператор в блоці Execute або значення Terminated встане в True (випадки висмикування з розетки або знеструмлення мікрорайону я тут не розглядаю).

Варіанти NewThread.Free. NewThread = nil хорошого результату не принесуть. Такі способи можуть примусово зупинити потік і викликати блокування ресурсів або витоку пам'яті.

Для того, щоб потік коректно завершився, потрібно зробити наступне:

  • Дочекатися закінчення його виконання (тривіально, але це так)
  • Сказати потоку про те, що ти просиш його завершитися

Другий спосіб опишу детальніше: Це кооперативний метод роботи основного і дочірнього потоків. Треба викликати метод потоку Terminate. А всередині Execute запрограмувати перевірку якості Terminated. Після цього Execute буде періодично перевіряти наявність встановленого властивості Termnated і коли воно з'явиться, потік зупиниться і якщо стоїть FreeOnTerminate: = true коректно звільнить все ресурси (підчистить об'єкти, відпустить блокування та ін.)

відповідь даний 14 Серпня '15 о 15:44







Схожі статті