2012-03-16 155 views
7

我希望能夠在將某些項目添加到ObservableCollection後拒絕它們。我無法對ObservableCollection進行子類化或使用任何類型的視圖,所以我似乎僅限於使用定義的一個事件處理程序(CollectionChanged)在禁用的項目上執行.Remove()。如果項目在籌集和處理之間的短時間內存在,那很好;該項目應該不會持續在收集。在CollectionChanged事件處理程序中調用.Remove()似乎不被允許。在運行時.NET引發InvalidOperationException:從CollectionChanged事件處理程序中的ObservableCollection中刪除項目

「在CollectionChanged事件期間無法更改ObservableCollection。」

我個人認爲.NET應該允許我。如果我創建一個無限循環,這是我自己的缺陷。

我想用看起來像代碼:

myCollection.CollectionChanged += (sender, args) => 
{ 
    if (args.Action == NotifyCollectionChangedAction.Remove) 
     return; 
    foreach (var itm in myCollection) 
    { 
     if (itm.name == "Fred") 
      myCollection.Remove(itm); 
    } 
} 

我不知道我有哪些選擇。使用調度程序似乎不起作用。觸發另一個事件並將.Remove調用放入另一個處理程序是唯一想到的其他選項。

+0

您無法從ObservableCollection中刪除項目。這是一個整體的意義......你只能從它所包裝的集合中刪除項目。 – 2012-03-16 19:36:49

+0

您不應該在集合已更改的事件處理程序中執行此操作。在允許更改集合之前,請先執行過濾器。如果它沒有適當的變化,不要讓集合被改變。 – 2012-03-16 19:39:05

+0

我知道這是舊的,可​​能不是'正確'的方法;但這是我所做的並可能幫助某人。當我嘗試從OberservableCollection中刪除選定的文件時,我遇到了同樣的問題。當我的Messenger處理第二個文件刪除請求時,CollectionChange事件仍在激發。因此,在我的CollectionChanged事件處理程序中,我必須添加'lock(this.Files){//事件代碼}'一旦我這樣做了,我再次運行我的程序並選擇多個文件並點擊刪除。這一次沒有例外,因爲Remove必須等待。 – famousKaneis 2015-08-25 14:31:17

回答

11

如果你真的要修改你會想通過收集的副本迭代集合。因爲你正試圖修改foreach循環中的集合,這會導致你的悲傷。

例如

var copy = new ObservableCollection<YourType>(collection) 
foreach(var item in copy) 
{ 
    if(item.Name == "Fred") 
    { 
     collection.Remove(item); 
    } 

} 

這麼說,我與阿努拉格同意,你不應該做這種類型的事情有一個ObservableCollection,肯定不是一個CollectionChanged事件中。

0

使用ToList()爲了迭代列表。

foreach(var item in collection.ToList()) 
{ 
    if(item.Name == "Fred") 
    { 
     collection.Remove(item); 
    } 
} 
相關問題