標籤:blog http 使用 os io 資料 for cti
加菲貓Just have a little faith.C#弱引用
.NET架構提供了另一有趣的特色,被用於實現多樣的快取。在.NET中弱引用通過System.WeakReference類實現。弱引用為引用的對象提供一項機制,使被引用的對象能夠被垃
圾收集器作用。ASP.NET快取就使用了弱引用。如果記憶體使用量率太高,快取將被清除。
強制垃圾收集 .NET架構為開發人員提供System.GC類來控制垃圾收集器的一些方面。垃圾收集可以通過調用GC.Collect方法強制執行。通常建議不要手動的調用垃圾收集器,而將其設定為自動方式。在某些情況下,開發人員會發現強制垃圾收集將推進效能。但是,使用這個方法需要非常小心,因為在垃圾收集器運行時將延緩當前執行的線程。GC.Collect方法不應位於可能被經常調用的地方。這樣做將使應用程式的效能降級。
建構函式:
WeakReference 初始化 WeakReference 類的新執行個體。 此建構函式重載不能在基於 Silverlight 的應用程式中實現。
WeakReference(Object) 引用指定的對象初始化 WeakReference 類的新執行個體。
WeakReference(Object, Boolean) 初始化 WeakReference 類的新執行個體,引用指定的對象並使用指定的複活跟蹤。
屬性:
IsAlive 擷取當前 WeakReference 對象引用的對象是否已被記憶體回收的指示。
Target 擷取或設定當前 WeakReference 對象引用的對象(目標)。
TrackResurrection 擷取當前 WeakReference 對象引用的對象在終止後是否會被跟蹤的指示。
我們考慮使用弱引用的時候:
對象稍後可能被使用,但不是很確定。(如果確定要使用,就應該用強引用)
如果需要,對象可以重新被構造出來(比如資料庫構造)。
對象占相對比較大的記憶體(一般大於幾KB以上)
在某些場合,例如緩衝某些大資料對象的時候,會遇到記憶體與時間的兩難境況,如果讓大對象過快的到期,那麼每次建立對象會消耗過多的效能,反之,保持了過多的大對象,那
麼記憶體將耗盡,反而降低速度。 如果記憶體尚且足夠,那麼GC就不會回收大對象佔用的記憶體,那麼弱引用就是可到達的,也就是說可以重用這個對象,達到緩衝的目的。如果記憶體不足,那麼GC就會不得不去回收那些大對象,從而釋放記憶體空間。
下面的程式碼範例示範如何使用弱引用將對象的緩衝作為應用程式的資源進行維護。 此緩衝是使用以索引值為關鍵字的 WeakReference 對象的 IDictionary(Of TKey, TValue) 構建的。 WeakReference 對象的 Target 屬性是一個表示資料的位元組數組中的對象。
此樣本將隨機訪問緩衝中的對象。 如果通過記憶體回收來回收對象,則將重建新的資料對象;否則,該對象會因弱引用而可訪問。
using System;using System.Collections.Generic;public class Program{ public static void Main() { // Create the cache. int cacheSize = 50; Random r = new Random(); Cache c = new Cache(cacheSize); string DataName = ""; // Randomly access objects in the cache. for (int i = 0; i < c.Count; i++) { int index = r.Next(c.Count); // Access the object by // getting a property value. DataName = c[index].Name; } // Show results. double regenPercent = c.RegenerationCount * 100 / c.Count; Console.WriteLine("Cache size: {0}, Regenerated: {1}%", c.Count.ToString(), regenPercent.ToString()); }}public class Cache{ // Dictionary to contain the cache. static Dictionary<int, WeakReference> _cache; // Track the number of times an // object is regenerated. int regenCount = 0; public Cache(int count) { _cache = new Dictionary<int, WeakReference>(); // Add data objects with a // short weak reference to the cache. for (int i = 0; i < count; i++) { _cache.Add(i, new WeakReference(new Data(i), false)); } } // Returns the number of items in the cache. public int Count { get { return _cache.Count; } } // Returns the number of times an // object had to be regenerated. public int RegenerationCount { get { return regenCount; } } // Accesses a data object from the cache. // If the object was reclaimed for garbage collection, // create a new data object at that index location. public Data this[int index] { get { // Obtain an instance of a data // object from the cache of // of weak reference objects. Data d = _cache[index].Target as Data; if (d == null) { // Object was reclaimed, so generate a new one. Console.WriteLine("Regenerate object at {0}: Yes", index.ToString()); d = new Data(index); regenCount++; } else { // Object was obtained with the weak reference. Console.WriteLine("Regenerate object at {0}: No", index.ToString()); } return d; } }}// This class creates byte arrays to simulate data.public class Data{ private byte[] _data; private string _name; public Data(int size) { _data = new byte[size * 1024]; _name = size.ToString(); } // Simple property. public string Name { get { return _name; } }}// Example of the last lines of the output://// ...// Regenerate object at 36: Yes// Regenerate object at 8: Yes// Regenerate object at 21: Yes// Regenerate object at 4: Yes// Regenerate object at 38: No// Regenerate object at 7: Yes// Regenerate object at 2: Yes// Regenerate object at 43: Yes// Regenerate object at 38: No// Cache size: 50, Regenerated: 94%//