Версия для печати темы
Нажмите сюда для просмотра этой темы в оригинальном формате
Форум программистов > Delphi: Общие вопросы > Удаление объектов из большого кол-ва списков


Автор: GePo 17.3.2006, 09:40
У меня при выполнении программы есть много объектов и списков этих объектов. Если я захочу удалить какой-нибудь объект, то мне придется искать его во всех списках, чтобы удалить и из них, но этого делать крайне не хочется.
Что сделал я: создал что-то наподибие итератора из С++, которые безопасно перебирал бы все объекты списка. Т.е., просматривая очередной объект списка, смотреть - а существует ли он? Если нет, то сразу перейти к следующему объекту, удалив фиктивный. Тогда, мне достаточно просто удалить объект один раз, а из списков он удалиться автоматически.
Загвоздка вышла в том, а как определить, существует ли объект? Т.е., например у меня есть ссылка на объект obj : TMyClass, как определить, что объект в obj сущетсвует? Что сделал я:
Код

TMyClass = class
.........
                     function Noop : Boolean; virtual;
                  end;
..............

function TMyClass.Noop : Boolean;
begin
  result := true;
end;


и проверяю соотвественно так:
Код

try
  ....
  if obj.Noop then
    break;
except
  continute;
end;


Так вот, проблема в том, что даже если obj не существует, Noop все равно может вызываться, возвращать значение и не генерировать исключение.
Как тогда проверить, существует объект или нет? Либо есть другой способ простого удаления объекта из всех списков?

Автор: Snowy 17.3.2006, 10:11
Удаляй объект по FreeAndNil(obj)
После этого проверить элементарно: if Assign(obj) then существует

Автор: GePo 17.3.2006, 10:18
Нет, может я непонятно объснил, но в списке хранятся ссылки на сами объекты, а не указатели на одну переменную. Т.е. FreeAndNil(Obj) - удалит объект Obj и занулит какую-то текущую ссылку на объект. А все остальные ссылки на этот же объект он не тронет.

Автор: Демо 17.3.2006, 10:18
Разные варианты.

1. Построить систему извещений (Notification)
Примерная схема:
Каждый объект-список при создании регистрируется в еще одном списке - список извещаемых объектов.
Любой объект, помещаемый в объекты списки должен иметь метод извещения этих списков, а списки должны уметь эти извещения обрабатывать, соответственно.

2. Использовать твою схему, но вот так:
Код

 private 
    FExists: Boolean;
 public
    property Exists: Boolean read  FExists;


в конструкторе:
Код

FExists := True;

в деструкторе:
Код

FExists := False;


Ну а проверка понятно:
Код

try    
  ....    
  if obj.Exists then    
    break;    
except    
  continute;    
end;


Я бы предпочел первый метод, так как создание исключительной ситуации для проверки не есть хорошо и быстро при работе с большим количеством объектов.

Автор: GePo 17.3.2006, 10:34
Спасибо огромное, сделал пока вторым способом, т.к. списков у меня много, а удаление объектов будет происходить очень редко, так что система оповещений может оказатся довольно таки накладной. Хотя может ошибаюсь, но все равно идею приму на разработку, может выйдет более качественне, чем есть сейчас и еще раз спасибо.

Автор: Snowy 17.3.2006, 10:54
3. Создать реестр объектов - отдельный , где объекты регистрируются при создании и удаляются оттуда при уничтожении. Если в реестре нет - значит мертв.
4. Реестр списков объектов. Заносить в реестр все списки, а уничтожать объекты не вручную, а через процедуру, которая сначала произведет поиск во всех списках и везде поудаляет.

Автор: GePo 17.3.2006, 11:10
ну чтож, ИМХО
3. не удобно работать
4. аналог системы оповещений, только термины другие.

Автор: Alexeis 17.3.2006, 11:16
Цитата

уничтожать объекты не вручную, а через процедуру, которая сначала произведет поиск во всех списках и везде поудаляет.

лучше чтоб этой процедурой и был деструктор объекта.
я както делал такую штуку работает нормально.

Powered by Invision Power Board (http://www.invisionboard.com)
© Invision Power Services (http://www.invisionpower.com)