Verwalten von Objektlebensdauern durch Verweiszählung

In herkömmlichen Objektsystemen wird der Lebenszyklus von Objekten – d. h. die Probleme beim Erstellen und Löschen von Objekten – implizit von der Sprache (oder der Laufzeit der Sprache) oder explizit von Anwendungsprogrammierern behandelt.

In einem sich entwickelnden, dezentral konstruierten System, das aus wiederverwendeten Komponenten besteht, ist es nicht mehr wahr, dass jeder Client oder sogar jeder Programmierer immer "weiß", wie mit der Lebensdauer einer Komponente umzugehen ist. Für einen Client mit den richtigen Sicherheitsberechtigungen ist es immer noch relativ einfach, Objekte über eine einfache Anforderung zu erstellen, aber das Löschen von Objekten ist eine andere Angelegenheit. Es ist nicht unbedingt klar, wann ein Objekt nicht mehr benötigt wird und gelöscht werden sollte. (Leser, die mit Garbage Collection-Programmierumgebungen wie Java vertraut sind, sind möglicherweise anderer Meinung. Java-Objekte erstrecken sich jedoch nicht über Computer- oder sogar Prozessgrenzen, und daher ist die Garbage Collection auf Objekte beschränkt, die sich in einem Einzelprozessbereich befinden. Darüber hinaus erzwingt Java die Verwendung einer einzelnen Programmiersprache.) Selbst wenn der ursprüngliche Client mit dem Objekt fertig ist, kann er das Objekt nicht einfach herunterfahren, da einige andere Clients oder Clients möglicherweise noch einen Verweis darauf haben.

Eine Möglichkeit, sicherzustellen, dass ein Objekt nicht mehr benötigt wird, besteht darin, vollständig von einem zugrunde liegenden Kommunikationskanal abhängig zu sein, um das System zu informieren, wenn alle Verbindungen zu einem prozessübergreifenden oder kanalübergreifenden Objekt nicht mehr vorhanden sind. Systeme, die diese Methode verwenden, sind jedoch aus mehreren Gründen inakzeptabel. Ein Problem besteht darin, dass es einen großen Unterschied zwischen dem prozessübergreifenden/netzwerkübergreifenden Programmiermodell und dem Single-Process-Programmiermodell erfordern könnte. Im prozessübergreifenden/netzwerkübergreifenden Programmiermodell würde das Kommunikationssystem die für die Verwaltung der Objektlebensdauer erforderlichen Hooks bereitstellen, während im Programmiermodell für einzelne Prozesse Objekte direkt ohne dazwischen liegende Kommunikationskanäle verbunden sind. Ein weiteres Problem besteht darin, dass dieses Schema auch zu einer Ebene von vom System bereitgestellter Software führen könnte, die die Komponentenleistung im Prozessfall beeinträchtigen würde. Darüber hinaus würde ein Mechanismus, der auf expliziter Überwachung basiert, nicht dazu neigen, auf viele Tausende oder Millionen von Objekten zu skalieren.

COM bietet einen skalierbaren und verteilten Ansatz für diese Gruppe von Problemen. Clients teilen einem Objekt mit, wann sie es verwenden und wann sie fertig sind, und Objekte löschen sich selbst, wenn sie nicht mehr benötigt werden. Dieser Ansatz erfordert, dass alle Objekte Verweise auf sich selbst zählen. Programmiersprachen wie Java, die inhärent über eigene Schemas zur Verwaltung der Lebensdauer verfügen, z. B. Garbage Collection, können die Referenzzählung von COM verwenden, um COM-Objekte intern zu implementieren und zu verwenden, sodass der Programmierer sich nicht damit beschäftigen kann.

Ebenso wie eine Anwendung Arbeitsspeicher freigeben muss, der zugewiesen wurde, sobald der Arbeitsspeicher nicht mehr verwendet wird, ist ein Client eines Objekts dafür verantwortlich, seine Verweise auf das Objekt freizugeben, wenn dieses Objekt nicht mehr benötigt wird. In einem objektorientierten System kann der Client dies nur tun, indem er dem Objekt eine Anweisung gibt, sich selbst zu befreien.

Es ist wichtig, dass die Zuordnung eines Objekts aufgehoben wird, wenn es nicht mehr verwendet wird. Die Schwierigkeit besteht darin, zu bestimmen, wann die Zuordnung eines Objekts aufgehoben werden kann. Dies ist mit automatischen Variablen (denen auf dem Stapel zugeordnet) einfach. Sie können nicht außerhalb des Blocks verwendet werden, in dem sie deklariert werden, sodass die Zuordnung vom Compiler aufgehoben wird, wenn das Ende des Blocks erreicht ist. Bei COM-Objekten, die dynamisch zugeordnet werden, liegt es an den Clients eines Objekts, zu entscheiden, wann sie das Objekt nicht mehr verwenden müssen, insbesondere lokale oder Remoteobjekte, die möglicherweise von mehreren Clients gleichzeitig verwendet werden. Das -Objekt muss warten, bis alle Clients damit fertig sind, bevor es sich selbst freigibt. Da COM-Objekte über Schnittstellenzeiger bearbeitet werden und von Objekten in verschiedenen Prozessen oder auf anderen Computern verwendet werden können, kann das System die Clients eines Objekts nicht nachverfolgen.

Die COM-Methode, um zu bestimmen, wann die Zuordnung eines Objekts aufgehoben werden sollte, ist die manuelle Verweiszählung. Jedes Objekt verwaltet eine Verweisanzahl, die nachverfolgt, wie viele Clients mit ihm verbunden sind, d. h. wie viele Zeiger auf eine seiner Schnittstellen in einem Client vorhanden sind.

Weitere Informationen finden Sie in den folgenden Themen:

Verwenden und Implementieren von IUnknown