Programování

Moje dva centy za slabé reference v .Net

GC je zběhlý v získávání paměti obsazené spravovanými objekty. Měli byste však přijmout další opatření k usnadnění uvolňování paměti pro lepší výkon vašich aplikací.

Slabý odkaz je ten, který odkazuje na objekt v paměti a zároveň umožňuje garbage collectoru shromažďovat objekt nebo uvolňovat paměť obsazenou objektem při spuštění GC. Objekt, který je dosažitelný, není odpadky shromážděné modulem runtime.

Slabé reference můžete použít pro objekty, které spotřebovávají hodně paměti. Při použití slabých odkazů pro takové objekty povolíte, aby tyto objekty byly shromažďovány, zatímco současně umožníte, aby byly tyto objekty v případě potřeby znovu vytvořeny později. Takže pokud máte ve své aplikaci velký objekt, který byste používali méně často, můžete použít slabý odkaz na takové objekty za předpokladu, že opětovné vytvoření takových objektů není tak drahé.

Všimněte si, že když vytvoříte slabý odkaz na objekt, IntPtr do GCHandle se uloží interně pomocí slabého odkazu, který jste vytvořili. Modul runtime používá tento GCHandle ke správě tabulky, která obsahuje slabé odkazy na objekty. Pokud již byl objekt odstraněn z paměti, hodnota IntPtr bude IntPtr.Zero. Po dokončení slabého odkazu na objekt je odstraněn odpovídající záznam slabého odkazu na objekt v tabulce slabých odkazů. Pokud slabý odkaz na objekt je stále naživu a vyvoláte Target vlastnost na slabém odkazu, je vrácen skutečný objekt, na který ukazuje GCHandle slabého odkazu.

Vytvoření slabého odkazu na objekt nezvyšuje životnost objektu. Umožňuje garbage collector kultivovat paměť obsazenou objektem, pokud neexistují žádné silné odkazy na tento objekt. Rozdíl mezi slabým a silným odkazem na objekt spočívá v tom, že zatímco první stále umožňuje sběrateli odpadků získat paměť obsazenou tímto objektem, silný odkaz na objekt neumožňuje sběrateli odpadků získat paměť obsazenou ten objekt, pokud je na něj dosažitelný.

Programování slabé reference v C #

Chcete-li vytvořit slabý odkaz, budete muset využít výhody třídy System.WeakReference. Jakmile vytvoříte slabý odkaz na objekt, můžete pomocí vlastnosti Target slabého odkazu, který jste vytvořili, zkontrolovat, zda je původní objekt stále naživu. Následující fragment kódu ukazuje, jak můžete vytvořit slabý odkaz na objekt.

Obdélník obdélník = nový Obdélník (15, 10);

var slabáReference = nová WeakReference (obdélník);

Vlastnost IsAlive můžete použít ke kontrole, zda je slabý odkaz na objekt stále naživu. Tady je seznam kódů, který to ilustruje.

static void Main (řetězec [] args)

        {

Obdélník obdélník = nový Obdélník (15, 10);

var slabáReference = nová WeakReference (obdélník);

obdélník = null;

bool isAlive = slabýReference.IsAlive;

if (isAlive)

Console.WriteLine ("Objekt je stále naživu");

Console.Read ();

        }

Pokud silný odkaz na objekt již není k dispozici, můžete využít vlastnost Target slabého odkazu k použití objektu, jak je znázorněno ve fragmentu kódu uvedeném níže.

bool isAlive = slabýReference.IsAlive;

if (isAlive)

{

Obdélník obdélník = slabýReference. Cíl jako Obdélník;

// Nyní můžete použít obdélníkový objekt jako obvykle

}

Krátké a dlouhé slabé odkazy

Slabé reference mohou být buď krátkodobé, nebo dlouhodobé. Primární rozdíl mezi krátkou a slabou referencí spočívá v tom, že zatímco v prvním případě se vlastnost Target slabé reference stane nulovou, pokud GC získá objekt, v druhém případě je dlouhá slabá reference živá i po spuštění GC, tj. přežije cyklus GC. Všimněte si, že byste měli používat dlouhé slabé reference opatrně, protože po dokončení nelze předpovědět stav objektu.

V zásadě byste měli používat krátké slabé reference, pokud chcete použít objekt, který je v použitelném stavu. Naopak, dlouhá slabá reference je dobrou volbou, pokud chcete použít objekt bez ohledu na jeho stav. Chcete-li vytvořit dlouhý slabý odkaz, musíte při vytváření slabého odkazu předat „true“ jako druhý parametr přetíženému konstruktoru třídy WeakReference. Následující fragment kódu to ilustruje.

Obdélník obdélník = nový Obdélník (15, 10);

var slabReference = nový WeakReference (obdélník, true);