筛选对象C#的ObservableCollection

本文关键字:ObservableCollection 对象 筛选 | 更新日期: 2023-09-27 18:03:37

我想为我的Xamarin Form应用程序按名称筛选Person对象的ObservableCollection。目标是过滤这个ObservableCollection,只显示它的一部分

这是我的Person对象类:

public class Person
{
    public string Name { get; set; }
    public string Address { get; set; }
    public string Phone { get; set; }
}

我试着做一个这样的过滤器:

private ObservableCollection<Person> personItems = new ObservableCollection<Person>();
public ObservableCollection<Person> PersonItems
{
    get { return personItems; }
    set { personItems = value; OnPropertyChanged(); }
}
public void FilterPerson(string filter)
{
    if (string.IsNullOrWhiteSpace(filter))
    {
        PersonItems = personItems;
    }
    else 
    {
        PersonItems = personItems.Where((person) => person. Name.ToLower().Contains(filter));
        // Error here
    }
}

我有这个错误:

无法显式转换类型:’系统。集合。通用的IEnumerable'到’系统。集合。ObjectModel。ObservableCollection

筛选对象C#的ObservableCollection

基本上有两种解决方案:

  1. 如果您的PersonsItems列表不是很大,那么每次新的筛选器字符串到达时,您可能会重新创建一个完整的集合。在这种情况下,您甚至不需要ObservableCollection(因为您不更改集合本身,而是更改对集合的引用(。在这种情况下,所有UI元素都将被重新创建

    PersonItems = originalItems.Where((person) => person. Name.ToLower().Contains(filter)).ToList();
    
  2. 如果您的PersonsItems列表足够大,则第一个解决方案不是一个选项。在这种情况下,您需要对应该添加/删除的对象手动调用Add/Remove方法。ObservableCollection有一个命令式API,每次调用Add/Remove时都会触发一个事件。反过来,ItemsControl可以观察到此事件,它将进行相应的UI更改。Linq有一个声明性的API。这就是为什么你需要手动同步一个列表来显示一个经过筛选的列表。

PersonItems = personItems.Where((person) => person. Name.ToLower().Contains(filter));

正在返回IEnumerable。

PersonItems = new ObservableCollection<Person>(personItems.Where((person) => person.Name.ToLower().Contains(filter))); 替换

您必须使用过滤后的结果重新创建可观察的结果。

为了做到这一点,我在过去使用了James Montemagno的ObservableRangeCollection和Grouping辅助函数。你可以在这个插件中找到它们https://github.com/jamesmontemagno/mvvm-helpers