我有一个绑定到一组具有用于生成
我可以通过从集合中删除未保存的项(我必须在此阶段通知UI将其从字典中删除),保存到数据库,然后将其添加回集合中来解决此问题。这很麻烦,而且我并不总是能够从我的
编辑:针对Blam的答案:
我正在使用MVVM,因此已修改代码以使用绑定。要重现问题,请单击添加,选择项目,单击保存,重复此过程,然后尝试进行选择。我认为这证明了
GetHashCode()
结果的ID的项的ListBox
。当添加新项时,它的ID为0,直到首次保存到我们的数据库。这导致我的ListBox
出现问题;我认为原因是因为当项首次被ListBox
使用时,它存储在不期望哈希码更改的内部Dictionary
中。我可以通过从集合中删除未保存的项(我必须在此阶段通知UI将其从字典中删除),保存到数据库,然后将其添加回集合中来解决此问题。这很麻烦,而且我并不总是能够从我的
Save(BusinessObject obj)
方法访问该集合。是否有其他解决此问题的替代方案?编辑:针对Blam的答案:
我正在使用MVVM,因此已修改代码以使用绑定。要重现问题,请单击添加,选择项目,单击保存,重复此过程,然后尝试进行选择。我认为这证明了
ListBox
仍然在其内部Dictionary
中保留旧的哈希码,因此会出现冲突的键错误。<Window x:Class="ListBoxHashCode.MainWindow"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
Title="MainWindow" Height="350" Width="525">
<Grid>
<Grid.RowDefinitions>
<RowDefinition Height="Auto"/>
<RowDefinition Height="*"/>
</Grid.RowDefinitions>
<StackPanel HorizontalAlignment="Center" Orientation="Horizontal">
<Button Click="Button_Click_Add" Content="Add"/>
<Button Click="Button_Click_Save" Content="Save Selected"/>
</StackPanel>
<ListBox Grid.Row="1" ItemsSource="{Binding List}" DisplayMemberPath="ID" SelectedItem="{Binding Selected}"/>
</Grid>
</Window>
public partial class MainWindow : Window {
public ObservableCollection<ListItem> List { get; private set; }
public ListItem Selected { get; set; }
private Int32 saveId;
public MainWindow() {
this.DataContext = this;
this.List = new ObservableCollection<ListItem>();
this.saveId = 100;
InitializeComponent();
}
private void Button_Click_Add(object sender, RoutedEventArgs e) {
this.List.Add(new ListItem(0));
}
private void Button_Click_Save(object sender, RoutedEventArgs e) {
if (Selected != null && Selected.ID == 0) {
Selected.ID = saveId;
saveId++;
}
}
}
编辑2:在进行一些测试后,我发现了一些事情:
更改
ListBox
中项目的哈希码似乎可以正常工作。更改
ListBox
中选定项目的哈希码会破坏其功能。
当进行选择时(单个或多个选择模式),IList ListBox.SelectedItems
会更新。添加到选择中的项目将添加到 SelectedItems
,不再包括在选择中的项目将被删除。
如果在选定项目时更改项目的哈希码,则无法从 SelectedItems
中删除它。即使手动调用 SelectedItems.Remove(item)
、SelectedItems.Clear()
并将 SelectedIndex
设置为 -1,都没有效果,项目仍然位于 IList
中。这会导致在下一次选定它后抛出异常,因为我认为它又再次添加到了 SelectedItems
中。