Performansı İyileştirme: Nesne Davranışı

WPF nesnelerinin iç davranışını anlamak, işlevsellik ve performans arasında doğru dengeleri oluşturmanıza yardımcı olur.

Nesnelerdeki Olay İşleyicilerini Kaldırmamak Nesneleri Canlı Tutabilir

Bir nesnenin olayına geçirdiği temsilci, bu nesneye etkili bir başvurudur. Bu nedenle, olay işleyicileri nesneleri beklenenden daha uzun süre canlı tutabilir. Bir nesnenin olayını dinlemek üzere kaydedilmiş bir nesnenin temizleme işlemini gerçekleştirirken, nesneyi serbest bırakmadan önce bu temsilciyi kaldırmak önemlidir. Gereksiz nesneleri canlı tutmak, uygulamanın bellek kullanımını artırır. Bu özellikle nesne bir mantıksal ağacın veya görsel ağacın kökü olduğunda geçerlidir.

WPF, kaynak ve dinleyici arasındaki nesne ömrü ilişkilerinin izlenmesinin zor olduğu durumlarda yararlı olabilecek olaylar için zayıf bir olay dinleyicisi düzeni sunar. Bazı mevcut WPF olayları bu düzeni kullanır. Nesneleri özel olaylarla uyguluyorsanız, bu desen sizin için kullanımda olabilir. Ayrıntılar için bkz . Zayıf Olay Desenleri.

ClR Profil Oluşturucu ve Çalışma Kümesi Görüntüleyicisi gibi belirli bir işlemin bellek kullanımı hakkında bilgi sağlayabilecek çeşitli araçlar vardır. CLR Profiler ayrılmış türlerin histogramı, ayırma ve çağrı grafikleri, çeşitli nesillerin çöp toplamalarını gösteren bir zaman çizelgesi ve bu koleksiyonlardan sonra yönetilen yığının sonuç durumu ve yöntem başına ayırmaları ve derleme yüklerini gösteren bir çağrı ağacı gibi ayırma profilinin çok yararlı bir dizi görünümünü içerir. Daha fazla bilgi için bkz . Performans.

Bağımlılık Özellikleri ve Nesneleri

Genel olarak, bir DependencyObject öğesinin bağımlılık özelliğine erişmek, CLR özelliğine erişmekten daha yavaş değildir. Özellik değerini ayarlamak için küçük bir performans yükü olsa da, bir değeri almak, clr özelliğinden değer almak kadar hızlıdır. Küçük performans yükünün sıfırlanması, bağımlılık özelliklerinin veri bağlama, animasyon, devralma ve stil oluşturma gibi güçlü özellikleri desteklemesidir. Daha fazla bilgi için bkz . Bağımlılık Özelliklerine Genel Bakış.

DependencyProperty İyileştirmeleri

Uygulamanızda bağımlılık özelliklerini çok dikkatli bir şekilde tanımlamanız gerekir. gibi DependencyProperty diğer meta veri seçenekleri yerine yalnızca işleme türü meta veri seçeneklerini AffectsMeasureetkiliyorsanız, meta verilerini geçersiz kılarak bu şekilde işaretlemeniz gerekir. Özellik meta verilerini geçersiz kılma veya alma hakkında daha fazla bilgi için bkz . Bağımlılık Özelliği Meta Verileri.

Tüm özellik değişiklikleri ölçüyü, düzenlemeyi ve işlemeyi gerçekten etkilemiyorsa, bir özellik değişikliği işleyicisinin ölçüyü geçersiz kılması, geçişleri düzenlemesi ve işlemesi daha verimli olabilir. Örneğin, bir arka planı yalnızca bir değer ayarlanmış bir sınırdan büyük olduğunda yeniden işlemeye karar vekleyebilirsiniz. Bu durumda, özellik değişikliği işleyiciniz yalnızca değer ayarlanan sınırı aştığında işlemeyi geçersiz kılır.

DependencyProperty Devralınabilir Yapmak Ücretsiz Değil

Varsayılan olarak, kayıtlı bağımlılık özellikleri devralınamaz. Ancak, herhangi bir özelliği açıkça devralınabilir yapabilirsiniz. Bu kullanışlı bir özellik olsa da, bir özelliği devralınabilir duruma dönüştürmek, özellik geçersiz kılınması için gereken süreyi artırarak performansı etkiler.

RegisterClassHandler'ı Dikkatle Kullanma

Çağrısı RegisterClassHandler örnek durumunuzu kaydetmenize olanak sağlarken, işleyicinin her örnekte çağrıldığını ve bu da performans sorunlarına neden olabileceğini unutmayın. Yalnızca uygulamanız örnek durumunuzu kaydetmenizi gerektirdiğinde kullanın RegisterClassHandler .

Kayıt Sırasında DependencyProperty için Varsayılan Değeri Ayarlama

Varsayılan değer gerektiren bir DependencyProperty oluştururken, parametresi olarak geçirilen varsayılan meta verileri kullanarak değerini yöntemine RegisterDependencyPropertyayarlayın. Bir oluşturucuda veya öğenin her örneğinde özellik değerini ayarlamak yerine bu tekniği kullanın.

Register kullanarak PropertyMetadata Değerini ayarlama

oluştururken DependencyPropertyveya OverrideMetadata yöntemlerini kullanarak Register öğesini ayarlama PropertyMetadata seçeneğiniz vardır. Nesnenizin çağrısı OverrideMetadataiçin statik bir oluşturucu olsa da, bu en uygun çözüm değildir ve performansı etkiler. En iyi performans için çağrısı sırasında değerini PropertyMetadata olarak Registerayarlayın.

Dondurulabilir Nesneler

A Freezable , iki durumu olan özel bir nesne türüdür: dondurulmamış ve dondurulmuş. Nesneleri mümkün olduğunda dondurmak uygulamanızın performansını artırır ve çalışma kümesini azaltır. Daha fazla bilgi için bkz . Freezable Objects Overview.

Her Freezable birinin her değiştiğinde tetiklenen bir Changed olayı vardır. Ancak, değişiklik bildirimleri uygulama performansı açısından maliyetlidir.

Her Rectangle birinin aynı Brush nesneyi kullandığı aşağıdaki örneği göz önünde bulundurun:

rectangle_1.Fill = myBrush;
rectangle_2.Fill = myBrush;
rectangle_3.Fill = myBrush;
// ...
rectangle_10.Fill = myBrush;
rectangle_1.Fill = myBrush
rectangle_2.Fill = myBrush
rectangle_3.Fill = myBrush
' ...
rectangle_10.Fill = myBrush

Varsayılan olarak WPF, nesnenin SolidColorBrush özelliğini geçersiz kılması için nesnenin ChangedRectangle olayı için bir olay Fill işleyicisi sağlar. Bu durumda, olayı her tetiklemesi SolidColorBrushChanged gerektiğinde, her Rectanglebiri için geri çağırma işlevini çağırmak gerekir; bu geri çağırma işlevi çağrılarının birikmesi önemli bir performans cezasına neden olur. Ayrıca, uygulamanın bunu yapmak için listenin tamamında dolaşması gerekeceğinden, bu noktada işleyici eklemek ve kaldırmak çok yoğun performans gerektirir. Uygulama senaryonuz değerini hiçbir zaman değiştirmezse SolidColorBrush, olay işleyicilerini gereksiz yere bakımının Changed maliyetini ödersiniz.

Freezable Artık değişiklik bildirimlerini korumak için kaynakları harcaması gerekmediğinden dondurulması performansını geliştirebilir. Aşağıdaki tabloda, özelliği olarak ayarlandığında truebasit SolidColorBrushIsFrozen bir değerin boyutu, olmadığı durumlarla karşılaştırıldığında gösterilmektedir. Bu, on Rectangle nesnenin özelliğine Fill bir fırça uygulandığını varsayar.

İl Büyüklük
Dondurulmuş SolidColorBrush 212 Bayt
Dondurulmayan SolidColorBrush 972 Bayt

Aşağıdaki kod örneği bu kavramı gösterir:

Brush frozenBrush = new SolidColorBrush(Colors.Blue);
frozenBrush.Freeze();
Brush nonFrozenBrush = new SolidColorBrush(Colors.Blue);

for (int i = 0; i < 10; i++)
{
    // Create a Rectangle using a non-frozed Brush.
    Rectangle rectangleNonFrozen = new Rectangle();
    rectangleNonFrozen.Fill = nonFrozenBrush;

    // Create a Rectangle using a frozed Brush.
    Rectangle rectangleFrozen = new Rectangle();
    rectangleFrozen.Fill = frozenBrush;
}
Dim frozenBrush As Brush = New SolidColorBrush(Colors.Blue)
frozenBrush.Freeze()
Dim nonFrozenBrush As Brush = New SolidColorBrush(Colors.Blue)

For i As Integer = 0 To 9
    ' Create a Rectangle using a non-frozed Brush.
    Dim rectangleNonFrozen As New Rectangle()
    rectangleNonFrozen.Fill = nonFrozenBrush

    ' Create a Rectangle using a frozed Brush.
    Dim rectangleFrozen As New Rectangle()
    rectangleFrozen.Fill = frozenBrush
Next i

Unfrozen Freezables üzerinde Değiştirilen İşleyiciler Nesneleri Canlı Tutabilir

Nesnenin bir nesnenin olayına Freezable geçirdiği temsilci, bu nesneye Changed etkili bir başvurudur. Bu nedenle, Changed olay işleyicileri nesneleri beklenenden daha uzun süre canlı tutabilir. Bir nesnenin olayını dinlemek üzere kaydedilmiş bir Freezable nesnenin temizleme işlemini gerçekleştirirken, nesneyi Changed serbest bırakmadan önce bu temsilciyi kaldırmak önemlidir.

WPF ayrıca olayları dahili olarak bağlar Changed . Örneğin, değer olarak alınan Freezable tüm bağımlılık özellikleri olayları otomatik olarak dinler Changed . Fill bir alan Brushözelliği bu kavramı gösterir.

Brush myBrush = new SolidColorBrush(Colors.Red);
Rectangle myRectangle = new Rectangle();
myRectangle.Fill = myBrush;
Dim myBrush As Brush = New SolidColorBrush(Colors.Red)
Dim myRectangle As New Rectangle()
myRectangle.Fill = myBrush

öğesine atanırken myBrushmyRectangle.Fill, nesneye işaret eden bir temsilci nesnenin ChangedRectangle olayına SolidColorBrush eklenir. Bu, aşağıdaki kodun aslında çöp toplama için uygun olmadığı myRect anlamına gelir:

myRectangle = null;
myRectangle = Nothing

Bu durumda myBrush hala canlıdır myRectangle ve olayını tetiklediğinde Changed onu geri çağırır. Yeni Rectangle bir özelliğine atamanın FillmyBrush öğesine başka bir olay işleyicisi myBrushekleyeceğini unutmayın.

Bu tür nesneleri temizlemenin önerilen yolu, özelliğinden Fill öğesini kaldırmaktır Brush ve bu da olay işleyicisini Changed kaldırır.

myRectangle.Fill = null;
myRectangle = null;
myRectangle.Fill = Nothing
myRectangle = Nothing

Kullanıcı Arabirimi Sanallaştırma

WPF ayrıca veriye bağlı alt içeriği otomatik olarak "sanallaştıran" öğenin bir çeşitlemesi StackPanel sağlar. Bu bağlamda virtualize sözcüğü, öğelerin ekranda göründüğü daha fazla sayıda veri öğesinden nesne alt kümesinin oluşturulduğu bir tekniği ifade eder. Belirli bir anda ekranda yalnızca birkaç kullanıcı arabirimi öğesi olduğunda çok sayıda kullanıcı arabirimi öğesi oluşturmak hem bellek hem de işlemci açısından yoğundur. VirtualizingStackPanel(tarafından VirtualizingPanelsağlanan işlevler aracılığıyla) görünür öğeleri hesaplar ve yalnızca görünür öğeler için öğe oluşturmak için öğesinden ItemsControl (veya ListViewgibiListBox) ile ItemContainerGenerator çalışır.

Performans iyileştirmesi olarak, bu öğeler için görsel nesneler yalnızca ekranda görünür durumdaysa oluşturulur veya canlı tutulur. Artık denetimin görüntülenebilir alanında olmadığında, görsel nesneler kaldırılabilir. Bu, veri nesnelerinin tümünün yerel koleksiyonda mevcut olmadığı veri sanallaştırmasıyla karıştırılmamalıdır. Gerektiğinde akışa alınır.

Aşağıdaki tabloda ve öğesine 5000 TextBlock öğe StackPanel ekleme ve işleme geçen süre gösterilmektedir VirtualizingStackPanel. Bu senaryoda ölçüler, bir nesnenin özelliğine ItemsSource metin dizesi ekleme ile panel öğelerinin ItemsControl metin dizesini görüntüleme zamanı arasındaki süreyi temsil eder.

Konak paneli İşleme süresi (ms)
StackPanel 3210
VirtualizingStackPanel 46

Ayrıca bkz.