C# 根据条件从列表中删除重复项
我有一个带有属性(名称、价格)的类项目 我想删除项目,只有当名称存在不止一次,价格是500美元使用LINQ,而不创建自定义比较器?对于以上一项,带$500的1将从列表中删除C# 根据条件从列表中删除重复项,c#,linq,c#-4.0,C#,Linq,C# 4.0,我有一个带有属性(名称、价格)的类项目 我想删除项目,只有当名称存在不止一次,价格是500美元使用LINQ,而不创建自定义比较器?对于以上一项,带$500的1将从列表中删除 谢谢,查找重复项目可以通过以下方式完成: var dups = lst.Where(x=>lst.Any(y => y != x && y.Name == x.Name)) var dups500 = dups.Where(x=>x.Price == 500); 可以通过以下方式查找价格
谢谢,查找重复项目可以通过以下方式完成:
var dups = lst.Where(x=>lst.Any(y => y != x && y.Name == x.Name))
var dups500 = dups.Where(x=>x.Price == 500);
可以通过以下方式查找价格500
的重复项目:
var dups = lst.Where(x=>lst.Any(y => y != x && y.Name == x.Name))
var dups500 = dups.Where(x=>x.Price == 500);
最后,可以使用EXPECT方法删除dups500:
var result = lst.Except(dup);
或一应俱全:
var result =
lst.Except(
lst
.Where(x=>x.Price == 500 &&
lst.Any(y => y != x && y.Name == x.Name))).ToList();
//这里有指定条件的项目列表。从基础集合中删除它们尝试以下操作:
var result = items
.GroupBy(item => item.Name)
.SelectMany(g => g.Count() > 1 ? g.Where(x => x.Price != 500) : g);
第一组的名字。如果组中有多个项目,请仅从价格不为500的组中选择项目。我将首先创建一个包含重复项的预评估子集列表:
var result =
from item in items
where item.Price != 500 || items.Count(i => i.Name == item.Name) == 1
select item;
var dupes = list.Where(a => list.Count(b => b.Name.Equals(a.Name)) > 1).ToList();
.ToList()
确保此查询只计算一次。如果列表很大,这将在速度上产生巨大的差异
现在,如果您的列表是列表
,则可以使用RemoveAll()
方法:
list.RemoveAll(item => item.Price == 500 && dupes.Contains(item));
你完成了
但是,如果您的列表只有IEnumerable
,或者您不想修改源列表,或者您想要延迟执行,那么只需使用LINQ:
var result = list.Where(item => !(item.Price == 500 && dupes.Contains(item)));
这将在枚举结果时进行计算
我想删除项目只有当名称存在不止一次,价格是500美元
var Test=(来自DataTable.AsEnumerable()中的行)
选择row.Field(“ColumnName”).Distinct();
@KirkWoll,这取决于你的口味,但并不令人困惑:除外
表示除外
,而内部搜索具有给定条件的项目似乎很简单:)但这取决于你的选择。(这也比groupby one快)。这并不能同时保持两者的一致性Item3s@MartinNeal,我不明白你的意思?@Saeed:除了
返回两个序列的“集差”(即,它排除重复项)。由于OP的示例中有两个项目带有{Name=“Item3”,Price=$150}
,因此这些项目中的一个可能会被排除在外,除了
(例如,如果它们是相同的对象;或者如果它们具有将它们视为相等的Equals
方法;或者如果您使用将它们视为相等的IEqualityComparer
)。但是,如果它们不被认为是相等的,并且它们只是两个碰巧具有相同名称和价格的对象,那么您就没事了。嗯,这取决于OP对其Item类的定义。我使用匿名类进行了测试,y!=x部分的行为不同。这将删除价格为500的项目,即使它不是重复的。1准备好这些好东西。
Apple 300 <-- winner
Apple 500 <-- dupe
Banana 500 <-- winner
Banana 500 <-- dupe
Banana 500 <-- dupe
Cantelope 100 <-- winner
Cantelope 200 <-- winner
from item in source
group item by item.Name into g
let okItems = g.Where(x => x.Price != 500)
let secondChoiceItem = g.FirstOrDefault(x => x.Price == 500)
let theItems = okItems.DefaultIfEmpty(secondChoiceItem)
from nonDupeItem in theItems
select nonDupeItem
var Test = (from row in DataTable.AsEnumerable()
select row.Field<string>("ColumnName")).Distinct();