Je sais que ViewData et ViewBag utilisent tous deux les mêmes données de support et que ni l'un ni l'autre ne sont aussi bons que l'utilisation de modèles fortement typés dans la plupart des cas. Cependant, lorsque vous choisissez entre les deux, la nature dynamique de ViewBag est-elle plus lente que l'utilisation de ViewData?
Réponses
Trop de publicités?Ok - ma première réponse est simplement dit " non " à temps pour un peu d'un demi-tour.
Il devrait être " non " dans un parfait dynamique du monde - mais regardant de plus près, il semblerait qu'il y aura soit pas de différence (comptabilité pour JIT magie) ou il pourrait être très légèrement plus lent, mais pas assez pour justifier de ne pas l'utiliser (je le suis).
En théorie , si elle est correctement mise en œuvre, le ViewBag serait, en définitive, de surperformer l'utilisation de la ViewData dictionnaire, parce que la liaison des expressions (par exemple, ViewBag.Foo
) est très bien mis en cache à travers les différents CallSites que le compilateur va générer (refléter une méthode de lecture ou d'écriture à l' ViewBag
et vous verrez ce que je veux dire).
La mise en cache des couches de la DLR sont bien documentés (même si un peu difficile à comprendre, une fois que vous obtenez en profondeur) mais au fond, l'exécution fait de son mieux pour "se souvenir" où une valeur donnée d'instance est une fois sa limite - par exemple par le biais d'un Ensemble ou d'Obtenir de l'énoncé.
MAIS La mise en cache, de son utilisation et de son efficacité, est entièrement dépendant de la implémentations sous-jacentes de classes/interfaces comme DynamicObject, idynamicmetaobjectprovider fournie par etc; ainsi que le résultat final de la Get/Set expression de liaison.
Dans le cas de la MVC interne DynamicViewDataDictionary de classe, au final, il finit par se liant à ceci:
public override bool TryGetMember(GetMemberBinder binder, out object result)
{
result = this.ViewData[binder.Name];
return true;
}
Pour var a = ViewBag.Foo
Et
public override bool TrySetMember(SetMemberBinder binder, object value)
{
this.ViewData[binder.Name] = value;
return true;
}
Pour ViewBag.Foo = Bar;
En d'autres termes, les états sont effectivement d'être réécrit pour wrappers autour du dictionnaire de l'indexeur.
À cause de cela, il n'y a certainement pas de la façon dont il pourrait être plus rapide que de le faire vous-même.
Ont été ViewData
à se nourrir d' ViewBag
, au lieu de l'inverse, et avait ViewBag
alors été mis en œuvre avec même quelque chose comme ExpandoObject
, alors il pourrait être une autre histoire - comme la dynamique de la mise en œuvre de l' ExpandoObject
est beaucoup plus intelligente et la mise en cache des règles qu'il emploie permettre pour certains assez cool d'exécution des optimisations.
En Conclusion
(merci à Shawn McLean pour suggérant une a été nécessaire!)
ViewBag sera plus lente que ViewData; mais probablement pas assez pour justifier l'inquiétude.
Je n'ai fait aucun test, mais mon intuition est que dans des scénarios du monde réel, la différence est tout simplement négligeable. Vous y accéderez probablement plusieurs fois sur chaque page et quelques cycles CPU ne feront aucune différence. On peut trouver des améliorations de performances plus importantes dans d'autres endroits.