2015-03-27 2 views
0

Я отлаживаю некоторый код из библиотеки призмы Microsoft. А именно класс с именем ModuleCatalog:Рекурсия с C# Событие

public class AppModuleCatalog : IAppModuleCatalog 
{ 
    private readonly ModuleCatalogItemCollection _items; 
    private bool _isLoaded; 

    public Collection<IAppModuleCatalogItem> Items 
    { 
     get { return (Collection<IAppModuleCatalogItem>)this._items; } 
    } 

    public AppModuleCatalog() 
    { 
     this._items = new ModuleCatalogItemCollection(); 
     this._items.CollectionChanged += new NotifyCollectionChangedEventHandler(this.ItemsCollectionChanged); 
    } 

    public virtual void AddModule(AppModuleInfo moduleInfo) 
    { 
     Argument.IsNotNull("moduleInfo", moduleInfo); 

     this.Items.Add(moduleInfo); 
    } 

    public AppModuleCatalog AddModule(string moduleName, string moduleType, string refValue, InitializationMode initializationMode, params string[] dependsOn) 
    { 
     Argument.IsNotNull("ModuleName", moduleName); 
     Argument.IsNotNull("moduleType", moduleType); 

     AppModuleInfo moduleInfo = new AppModuleInfo(moduleName, moduleType); 

     moduleInfo.DependsOn.AddRange(dependsOn); 
     moduleInfo.InitializationMode = initializationMode; 
     moduleInfo.Ref = refValue; 
     this.Items.Add(moduleInfo); 

     return this; 
    } 

    private void ItemsCollectionChanged(object sender, NotifyCollectionChangedEventArgs e) 
    { 
     if (!this.Validated) 
      return; 
     this.EnsureCatalogValidated(); 
    } 
    . 
    . 
    . 

    private class ModuleCatalogItemCollection : Collection<IAppModuleCatalogItem>, INotifyCollectionChanged 
    { 
     public event NotifyCollectionChangedEventHandler CollectionChanged; 

     protected override void InsertItem(int index, IAppModuleCatalogItem item) 
     { 
      InsertItem(index,item); 
      this.OnNotifyCollectionChanged(new NotifyCollectionChangedEventArgs(NotifyCollectionChangedAction.Add, item, index)); 
     } 

     protected void OnNotifyCollectionChanged(NotifyCollectionChangedEventArgs eventArgs) 
     { 
      if (this.CollectionChanged == null) return; 
      this.CollectionChanged(this, eventArgs); 
     } 
    } 
} 

Когда этот класс инициализируется, метод AddModule называется, что добавит к ModuleInfo Items собственности. Я заметил, что частный класс затем вызывается, и рекурсивный вызов повторяется в методе InsertItem, который, конечно, вызывает исключение OverFlow. Обратите внимание, что свойство getter from Items возвращает _items

Не могли бы вы объяснить мне, почему происходит рекурсия?

ответ

1

Согласно original source code, реализация ModuleCatalogItemCollection.InsertItem(int, IModuleCatalogItem) метода выглядит следующим образом:

protected override void InsertItem(int index, IModuleCatalogItem item) 
{ 
    base.InsertItem(index, item); 

    this.OnNotifyCollectionChanged(new NotifyCollectionChangedEventArgs(NotifyCollectionChangedAction.Add, item, index)); 
} 

Примечание вызова base.InsertItem(index, item) метод. Это вызовет реализацию базового метода из класса Collection<IModuleCatalogItem>, а не this.InsertItem(). Таким образом, в этом месте нет рекурсивного вызова.

+0

Спасибо. Я понял это вчера. Вы избили меня до ответа, хотя =) –