gpt4 book ai didi

wpf - 清除 ObservableCollection 时,e.OldItems 中没有项目

转载 作者:行者123 更新时间:2023-12-03 05:02:06 26 4
gpt4 key购买 nike

这里有一些东西确实让我措手不及。

我有一个 T 的 ObservableCollection,其中充满了项目。我还有一个附加到 CollectionChanged 事件的事件处理程序。

当您清除集合时,它会引发 CollectionChanged 事件,并将 e.Action 设置为 NotifyCollectionChangedAction.Reset。好吧,这很正常。但奇怪的是,e.OldItems 和 e.NewItems 中都没有任何内容。 我希望 e.OldItems 填充从集合中删除的所有项目。

还有人看过这个吗?如果是这样,他们是如何解决这个问题的?

一些背景:我正在使用 CollectionChanged 事件来附加和分离另一个事件,因此如果我没有在 e.OldItems 中获得任何项目...我将无法从该事件分离。


澄清:我确实知道文档并没有完全声明它必须以这种方式运行。但对于其他所有操作,它都会通知我它做了什么。所以,我的假设是它会告诉我......在清除/重置的情况下也是如此。


如果您想自己重现,下面是示例代码。首先关闭 xaml:

<Window
x:Class="ObservableCollection.Window1"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
Title="Window1"
Height="300"
Width="300"
>
<StackPanel>
<Button x:Name="addButton" Content="Add" Width="100" Height="25" Margin="10" Click="addButton_Click"/>
<Button x:Name="moveButton" Content="Move" Width="100" Height="25" Margin="10" Click="moveButton_Click"/>
<Button x:Name="removeButton" Content="Remove" Width="100" Height="25" Margin="10" Click="removeButton_Click"/>
<Button x:Name="replaceButton" Content="Replace" Width="100" Height="25" Margin="10" Click="replaceButton_Click"/>
<Button x:Name="resetButton" Content="Reset" Width="100" Height="25" Margin="10" Click="resetButton_Click"/>
</StackPanel>
</Window>

接下来是后面的代码:

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Windows;
using System.Windows.Controls;
using System.Windows.Data;
using System.Windows.Documents;
using System.Windows.Input;
using System.Windows.Media;
using System.Windows.Media.Imaging;
using System.Windows.Navigation;
using System.Windows.Shapes;
using System.Collections.ObjectModel;

namespace ObservableCollection
{
/// <summary>
/// Interaction logic for Window1.xaml
/// </summary>
public partial class Window1 : Window
{
public Window1()
{
InitializeComponent();
_integerObservableCollection.CollectionChanged += new System.Collections.Specialized.NotifyCollectionChangedEventHandler(_integerObservableCollection_CollectionChanged);
}

private void _integerObservableCollection_CollectionChanged(object sender, System.Collections.Specialized.NotifyCollectionChangedEventArgs e)
{
switch (e.Action)
{
case System.Collections.Specialized.NotifyCollectionChangedAction.Add:
break;
case System.Collections.Specialized.NotifyCollectionChangedAction.Move:
break;
case System.Collections.Specialized.NotifyCollectionChangedAction.Remove:
break;
case System.Collections.Specialized.NotifyCollectionChangedAction.Replace:
break;
case System.Collections.Specialized.NotifyCollectionChangedAction.Reset:
break;
default:
break;
}
}

private void addButton_Click(object sender, RoutedEventArgs e)
{
_integerObservableCollection.Add(25);
}

private void moveButton_Click(object sender, RoutedEventArgs e)
{
_integerObservableCollection.Move(0, 19);
}

private void removeButton_Click(object sender, RoutedEventArgs e)
{
_integerObservableCollection.RemoveAt(0);
}

private void replaceButton_Click(object sender, RoutedEventArgs e)
{
_integerObservableCollection[0] = 50;
}

private void resetButton_Click(object sender, RoutedEventArgs e)
{
_integerObservableCollection.Clear();
}

private ObservableCollection<int> _integerObservableCollection = new ObservableCollection<int> { 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18, 19 };
}
}

最佳答案

它并不声称包含旧项目,因为重置并不意味着列表已被清除

这意味着发生了一些戏剧性的事情,并且计算添加/删除的成本很可能超过从头开始重新扫描列表的成本......所以这就是你应该做的。

MSDN 建议将整个集合重新排序为重置候选者的示例。

重申一下。 重置并不意味着清楚,它意味着您对列表的假设现在无效。将其视为一个全新的列表。 Clear 恰好是这种情况的一个例子,但很可能还有其他例子。

一些例子:
我有一个像这样的列表,其中包含很多项目,并且它已被数据绑定(bind)到 WPF ListView 以在屏幕上显示。
如果您清除列表并引发 .Reset 事件,性能几乎是即时的,但如果您引发许多单独的 .Remove 事件,则性能非常糟糕,因为WPF 将一项一项地删除。我还在自己的代码中使用了 .Reset 来指示列表已重新排序,而不是发出数千个单独的 Move 操作。与 Clear 一样,当引发许多单独的事件时,性能会受到很大影响。

关于wpf - 清除 ObservableCollection 时,e.OldItems 中没有项目,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/224155/

26 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com