Optimalizace výkonu: Datová vazba

Datová vazba WPF (Windows Presentation Foundation) je jednoduchý a konzistentní způsob, jakým aplikace můžou zobrazovat data a pracovat s nimi. Prvky mohou být vázány na data z různých zdrojů dat ve formě objektů CLR a XML.

Toto téma obsahuje doporučení k výkonu datových vazeb.

Způsob řešení odkazů na datové vazby

Než probereme problémy s výkonem datových vazeb, je vhodné prozkoumat, jak modul datových vazeb WPF (Windows Presentation Foundation) řeší odkazy na objekty pro vazbu.

Zdrojem datové vazby WINDOWS Presentation Foundation (WPF) může být libovolný objekt CLR. Můžete vytvořit vazbu na vlastnosti, dílčí vlastnosti nebo indexery objektu CLR. Vazbové odkazy jsou vyřešeny pomocí reflexe rozhraní Microsoft .NET Framework nebo ICustomTypeDescriptor. Tady jsou tři metody pro překlad odkazů na objekty pro vazbu.

První metoda zahrnuje použití reflexe. V tomto případě PropertyInfo se objekt používá ke zjištění atributů vlastnosti a poskytuje přístup k metadatům vlastnosti. Při použití ICustomTypeDescriptor rozhraní modul datových vazeb používá toto rozhraní pro přístup k hodnotám vlastností. Rozhraní ICustomTypeDescriptor je zvlášť užitečné v případech, kdy objekt nemá statickou sadu vlastností.

Oznámení o změnách vlastností lze poskytnout buď implementací INotifyPropertyChanged rozhraní, nebo pomocí oznámení o změnách přidružených k TypeDescriptorrozhraní . Upřednostňovanou strategií pro implementaci oznámení o změnách vlastností je však použití INotifyPropertyChanged.

Pokud je zdrojovým objektem objekt CLR a zdrojová vlastnost je vlastnost CLR, modul datových vazeb Windows Presentation Foundation (WPF) musí nejprve použít reflexi zdrojového objektu TypeDescriptork získání a následné dotazování na PropertyDescriptor. Tato posloupnost operací reflexe je z hlediska výkonu potenciálně velmi časově náročná.

Druhá metoda pro překlad odkazů na objekt zahrnuje zdrojový objekt CLR, který implementuje INotifyPropertyChanged rozhraní, a zdrojovou vlastnost, která je CLR vlastnost. V tomto případě modul datových vazeb používá odraz přímo na zdrojovém typu a získá požadovanou vlastnost. To stále není optimální metoda, ale bude stát méně v pracovních nastavených požadavcích než první metoda.

Třetí metoda pro překlad odkazů na objekt zahrnuje zdrojový objekt, který je DependencyObject a zdroj vlastnost, která je .DependencyProperty V tomto případě modul datových vazeb nemusí používat reflexi. Místo toho modul vlastností a modul datových vazeb společně přeloží odkaz na vlastnost nezávisle. Jedná se o optimální metodu pro překlad odkazů na objekty, které se používají pro datová vazba.

Následující tabulka porovnává rychlost vazby Text dat vlastnost jednoho tisíce TextBlock prvků pomocí těchto tří metod.

Vytvoření vazby vlastnosti TextBlock Čas vazby (ms) Doba vykreslování – zahrnuje vazbu (ms)
Na vlastnost objektu CLR 115 314
Vlastnost objektu CLR, který implementuje INotifyPropertyChanged 115 305
To a DependencyProperty of a DependencyObject. 90 263

Vazba na velké objekty CLR

Při vytváření vazby dat k jednomu objektu CLR s tisíci vlastností má významný dopad na výkon. Tento dopad můžete minimalizovat rozdělením jednoho objektu na více objektů CLR s menším počtem vlastností. Tabulka zobrazuje časy vazby a vykreslování datových vazeb na jeden velký objekt CLR a více menších objektů.

Datové vazby 1000 TextBlock objektů Čas vazby (ms) Doba vykreslování – zahrnuje vazbu (ms)
Na objekt CLR s 1000 vlastnostmi 950 1200
Na 1000 objektů CLR s jednou vlastností 115 314

Vazba na zdroj položek

Představte si scénář, ve kterém máte objekt CLR List<T> , který obsahuje seznam zaměstnanců, které chcete zobrazit v objektu ListBox. Chcete-li vytvořit korespondenci mezi těmito dvěma objekty, vytvořte vazbu seznamu zaměstnanců na ItemsSource vlastnost objektu ListBox. Předpokládejme ale, že se ke skupině připojíte nový zaměstnanec. Možná si myslíte, že pokud chcete tuto novou osobu vložit do vašich vázaných ListBox hodnot, jednoduše byste tuto osobu přidali do seznamu zaměstnanců a očekávali, že tato změna bude automaticky rozpoznána modulem datových vazeb. Tento předpoklad by prokázal nepravdivé; ve skutečnosti se změna neprojeví automaticky ListBox . Důvodem je to, že objekt CLR List<T> automaticky nevyvolá změněnou událost kolekce. Aby bylo možné ListBox změny vyzvednout, budete muset znovu vytvořit seznam zaměstnanců a znovu ho připojit k majetku ItemsSource objektu ListBox. I když toto řešení funguje, přináší obrovský dopad na výkon. Pokaždé, když znovu přiřazujete ItemsSourceListBox nový objekt, ListBox první vyhodí předchozí položky a znovu vygeneruje celý seznam. Dopad na výkon se zvětšuje, pokud se ListBox mapy mapují na komplexní DataTemplate.

Velmi efektivním řešením tohoto problému je vytvořit seznam ObservableCollection<T>zaměstnanců . Objekt ObservableCollection<T> vyvolá oznámení o změně, které může modul datových vazeb přijmout. Událost přidá nebo odebere položku z objektu ItemsControl , aniž by bylo nutné znovu vygenerovat celý seznam.

Následující tabulka ukazuje dobu potřebnou k aktualizaci ListBox (s vypnutou virtualizací uživatelského rozhraní) při přidání jedné položky. Číslo v prvním řádku představuje uplynulý čas, kdy je objekt CLR List<T> svázán s ListBox elementem ItemsSource. Číslo ve druhém řádku představuje uplynulý čas, kdy ObservableCollection<T> je vázán na ListBox prvek ItemsSource. Všimněte si významných časových úspor pomocí ObservableCollection<T> strategie datové vazby.

Datová vazba PoložkySource Čas aktualizace pro 1 položku (ms)
Do objektu CLR List<T> 1656
Na ObservableCollection<T> 20

Vazba IList na ItemsControl není IEnumerable

Pokud máte na výběr mezi vazbou objektu IList<T> nebo IEnumerable objektem ItemsControl , zvolte objekt IList<T> . Vazba IEnumerable na ItemsControl vynucování WPF k vytvoření objektu obálky IList<T> , což znamená, že výkon je ovlivněn zbytečným režijním zatížením druhého objektu.

Nepřeveďte objekty CLR na XML pouze pro datové vazby.

WPF umožňuje data svázání s obsahem XML; datové vazby k obsahu XML jsou však pomalejší než datové vazby k objektům CLR. Nepřeveďte data objektu CLR na XML, pokud je jediným účelem datové vazby.

Viz také