2008-08-20 13 views
3

В мире, где ручное распределение памяти и указатели по-прежнему править (Borland Delphi) Мне нужно общее решение для того, что я думаю, что это общая проблема:Как отслеживать ссылки на объект?

На данный момент объект можно ссылаться из нескольких мест (списков, другие объекты, ...). Есть ли хороший способ отслеживать все эти ссылки, чтобы я мог обновлять их, когда объект был уничтожен?

ответ

3

Если вы хотите уведомить других об изменениях, вы должны ввести "Observer Pattern". Delphi уже сделала это для вас для потомков TComponent. Вы можете вызвать метод TComponent.FreeNotification и сообщить о своем объекте, когда другой компонент будет уничтожен. Он делает это, вызывая метод уведомления. Вы можете удалить себя из списка уведомлений, вызвав TComponent.RemoveFreeNotification. Также см. this page.

Большинство сборщиков мусора не позволяют вам получить список ссылок, поэтому в этом случае они не помогут.Delphi может использовать подсчет ссылок, если вы будете использовать интерфейсы, но затем вам нужно будет самостоятельно отслеживать ссылки.

1

Я не могу понять, почему вы хотите это сделать. Наверняка, вы просто проверите ссылку не в Nil перед ее использованием?

Anwyays, два возможных решения я бы рассмотреть:

  1. Есть объекты менеджера свои собственные счетчики ссылок.
  2. Создайте класс менеджера подсчета ссылок.

Я бы добавил функции AddRef() и ReleaseRef() как к менеджеру, так и к соответствующему классу. Затем вы можете использовать их, чтобы проверить, сколько ссылок существует в любой момент. COM делает это так.

Класс, ориентированный на справочную систему, будет управлять только собственным счетчиком ссылок. Менеджер мог использовать карту для сопоставления указателей с целым числом для подсчета.

+0

+1 для второй идеи, подклассов TInterfacedObject (или строительство корневой класс, похожий на него) будет простой способ построить RefCount класс менеджера – mjn 2010-11-10 06:59:17

0

Вы пытаетесь отслеживать, кто ссылается на объект, чтобы вы могли очистить эти ссылки, когда объект был уничтожен, или вы пытаетесь отслеживать, когда можно безопасно уничтожить объект?

Если последнее, то похоже, что вы ищете сборщик мусора. Я никогда не имел дело с Delphi, поэтому я не знаю, есть ли GC для этого, который вы можете использовать, но я был бы удивлен, если бы не было.

Если бывший, то GC, вероятно, не поможет. Если Delphi поддерживает ООП/Наследование (честно, я не знаю, если это делает), вы могли бы сделать что-то вроде этого (псевдокод):

// Anything that will use one of your tracked objects implements this interface 
interface ITrackedObjectUser { 
    public void objectDestroyed(TrackedObject o); 
} 

// All objects you want to track extends this class 
class TrackedObject { 
    private List<ITrackedObjectUser> users; 

    public void registerRef(ITrackedObjectUser u) { 
    users.add(u); 
    } 

    public void destroy() { 
    foreach(ITrackedObjectUser u in users) { 
     u.objectDestroyed(this); 
    } 
    } 
} 

В основном, всякий раз, когда вы добавляете один из ваших отслеживаемых объектов в коллекции этой коллекции будет зарегистрируйтесь с этим объектом. Когда объект уничтожается (я полагаю, вы вызове destroy() в деструкторе объекта), тогда объект сигнализирует об уничтожении коллекции, чтобы коллекция могла делать все, что ей нужно.

К сожалению, это не очень хорошее решение, если вы хотите использовать сборные коллекции. Вам придется писать свои собственные объекты коллекции (они могут просто обернуть встроенные, хотя). И это потребует, чтобы вы регистрировались везде, где хотите отслеживать объект. Это не то, что я считаю «счастливым» решением, хотя для небольших проектов это, вероятно, было бы не так уж плохо. Я в основном надеюсь, что эта идея поможет породить другие идеи. :)

0

Есть ли у вас конкретная причина? Вы сталкиваетесь с проблемами с указателями изгоев, или вы думаете, что это может быть проблемой в один прекрасный день?

ИМХО это не будет проблемой, если вы правильно разработаете свое приложение, и использование соответствующих шаблонов действительно поможет вам.

Некоторая информация о скороговорки:

http://delphi.about.com/od/oopindelphi/a/aa010201a.htm

http://www.obsof.com/delphi_tips/pattern.html

Смежные вопросы