![]() |
| ||
|
|
Новости |
Поиск |
FAQ |
Статьи |
Книги |
Новости VCL
| | Форумы ЧАТ |
Орешник |
|
| |||
| |||
« предыдущая ветвь | форум | следующая ветвь »
Использование inherited
Mouserx © (2005-05-30 15:18:00)Есть у меня поток:
Метод Free я обьявляю так:
destructor TScriptThread.Destroy;
begin
inherited;
fFindedList.Free; {TStringList}
fIgnoreList.Free; {TStringList}
//inherited Destroy;
end;
Как я понял - Inherited вызывает обработчик предка. Где он должен стоять в моем варианте? в начале или в конце?
Digitman (2005-05-30 15:54:00) [41]
> При этом в основном потоке в Destroy
в Destroy какого класса ?
Defunct (2005-05-30 15:54:00) [42]Mouserx (30.05.05 15:51) [23]
> Поэтому там для всех созданных доп. потоков я вызывал просто метод Free каждому.
Чревато AV ошибками на выходе из программы.
Digitman (2005-05-30 15:52:00) [43]
> Mouserx (30.05.05 15:48) [21]
а что, без FreeOnTerminate=True никак не обойтись ?
что мешает в нужный момент разрушить поток извне ?
Mouserx (2005-05-30 15:51:00) [44]Digitman © (30.05.05 15:43) [19]
Задача такова. Есть дополнительный поток, в котором производяться медленные стороние вычисления.
Основной поток вызывает его используя метод Create. При этом в основном потоке в Destroy необходимо остановить и доп. потоки. Поэтому там для всех созданных доп. потоков я вызывал просто метод Free каждому.
Доп. поток, когда доделает свою работу - через метод Sinchronize() сообщить основному.
Defunct (2005-05-30 15:50:00) [45]Digitman © (30.05.05 15:43) [19]
Понимаю это так:
destructor TScriptThread.Destroy;
begin
inherited;
SendMessage( <Handle окна обработчика>, <Требование обработки List'ов>, xxx, xxx);
fFindedList.Free; {TStringList}
fIgnoreList.Free; {TStringList}
end;
Но что мешает сделать так:
destructor TScriptThread.Destroy;
begin
SendMessage( <Handle окна обработчика>, <Требование обработки List'ов>, xxx, xxx);
fFindedList.Free; {TStringList}
fIgnoreList.Free; {TStringList}
inherited;
end;
IMHO в деструкторе всегда inherited в конце, ничему не навредит и всегда будет работать. В крайнем случае можно засунуть inherited в finally.
Mouserx (2005-05-30 15:48:00) [46]
> -=XP=- © (30.05.05 15:43) [18]
Thread.Teminate;
Thread.WaitFor;
Это понятно.
Но зачем Tread.Free если поток сам освободится?
Tread.Free приведет к ошибке.
Да и насчет использования этой конструкции:
А если поток будет в состоянии ожидания Sinchronize()?
Получиться что поток ждет, пока освободится основной поток для выполнения Sinchronize() а тот в свою очередь ждет (Thread.WaitFor) пока закончит работу дополнительный поток
-=XP=- (2005-05-30 15:47:00) [47]По-моему, мы сейчас обсуждаем "через какую дверь лучше всего входить в метро".
-=XP=- (2005-05-30 15:43:00) [48]Но получается, что вызвав метод Free из основного потока - он пробежится по всему содержимому деструктора до inherited
Третья заповедь: Прежде чем рубить ветку, убедитесь, что Вы на ней не сидите (С) Энциклопедия юных сурков
Thread.Teminate;
Thread.WaitFor;
Tread.Free;
Digitman (2005-05-30 15:43:00) [49]
> Mouserx (30.05.05 15:31) [9]
местоположение inherited в дан.ситуации сильно зависит от того, кто вызывает деструктор
Mouserx (2005-05-30 15:42:00) [50]
> Используйте событие OnTerminate для уверенности. После обработки
> данных вызывайте Free
После метода Execute вызывается деструктор Destroy.
А зачем еще вызывать Free?
Defunct (2005-05-30 15:38:00) [51]Mouserx (30.05.05 15:36) [14]
Да, это событие происходит после окончания работы метода Execute
Digitman (2005-05-30 15:38:00) [52]
> Написал
>
> destructor TForm1.Create;
> begin
> ...
> end;
> И отладчик зашел в деструктор предка
какую-то галиматью ты написал)
Create() - это имя конструктора класса, а не деструктора
Mouserx (2005-05-30 15:36:00) [53]
> Используйте событие OnTerminate для уверенности
А будет ли это событие, если я поток трогать не буду а просто дождусь, пока он сам все сделает и выйдет?
Defunct (2005-05-30 15:36:00) [54]> TUser
destructorTForm1. Create; ??
TUser (2005-05-30 15:35:00) [55]> Mouserx (30.05.05 15:31) [9]
Они в дополнительном потоке и освободятся. По логике, если FreeOnTerminate = true, то не надо вызывать Free из основного потока, а надо писать Terminate;
Defunct (2005-05-30 15:34:00) [56]Mouserx (30.05.05 15:31) [9]
> Ну и поосвобождает 2 TSctrinList, работу с которыми я не закончил.
Используйте событие OnTerminate для уверенности. После обработки данных вызывайте Free.
TUser (2005-05-30 15:33:00) [57]> Digitman © (30.05.05 15:28) [8]
Может я чего-то не понял. Написал
destructor TForm1.Create;
begin
...
end;
без inherited. Поставил Use Debug DCUs. И отладчик зашел в деструктор предка.
Mouserx (2005-05-30 15:31:00) [58]Хм ... тогда я ничего не понял.
Вот мой коснструктор Create:
constructor TScriptThread.Create(Sender : TObject);
begin
inherited Create(True); {Поток создаем в состоянии «Приостановлен»}
FreeOnTerminate := True; {Поток освободит ресурсы при окончании работы}
fFindedList := TStringList.Create;
fIgnoreList := TStringList.Create;
Thread := Self;
Self.Priority := tpNormal; {Стартуем с нормальным приоритетом}
Resume; {Переводим поток в состояние «Активен»}
end;
В данном случае 2 TStringList я создаю после inherited Create(True);
Т.е как я понял освобождать их надо до Inherited Destroy.
Так?
Но получается, что вызвав метод Free из основного потока - он пробежится по всему содержимому деструктора до inherited. Ну и поосвобождает 2 TSctrinList, работу с которыми я не закончил.
Их же надо освобождать именно из дополнительного потока а не из основного. Что я не так сделал и не понял?
Digitman (2005-05-30 15:28:00) [59]
> TUser © (30.05.05 15:26) [7]
> На самом деле, дажде если не написать Inherited, то вызов
> унаследованного деструктора все равно происходит. По крайней
> мере в D7.
с какого перепугу-то ?
ты может быть путаешь собственно разрушение объекта с методом-деструктором ?
TUser (2005-05-30 15:26:00) [60]На самом деле, дажде если не написать Inherited, то вызов унаследованного деструктора все равно происходит. По крайней мере в D7.