假设我有这样一个业务对象,
class Employee
{
public string name;
public int id;
public string desgination;
public int grade;
}
List<Employee> lstEmp = new List<Employee>()
{
new Employee() { name="A",desgination="SE",id=1},
new Employee() { name="b",desgination="TL",id=2},
new Employee() { name="c",desgination="PL",id=3},
new Employee() { name="d",desgination="SE",id=4},
new Employee() { name="e",desgination="SSE",id=5},
};
如果我想将指定为“SE”的员工等级更新为 3,那么我必须这样写
lstEmp=lstEmp.Select(x =>
{
x.grade = (x.desgination == "SE") ? 3 : x.grade;
return x;
}).ToList();
但是这里使用 select 时每次都会生成新的员工对象,而不是更新现有的 lstEmp,所以我必须将更新后的列表重新分配给 lstEmp。
在我看来,频繁更新大型更新会影响性能。有解决办法吗?
最佳答案
实际上,您现有的 Select
调用是修改原始对象本身 - 它不是创建新的员工对象。是什么让您认为它正在创建新的 Employee
实例?毕竟,您在 lambda 表达式中的任何地方都没有 new Employee
。
您可以在不调用 ToList
的情况下遍历调用 Select
的结果,之后您仍然会看到更改。这意味着您的投影有副作用 - 这通常是个坏主意。不过,您确实必须对投影结果进行某些 迭代。例如,只需调用 Count()
即可。 LINQ 查询在许多情况下使用延迟执行:它们在需要结果之前不应用投影/谓词/等。
LINQ 旨在以函数式方式工作:不鼓励出现副作用,就像您不希望数据库上的普通 SELECT 查询更改其正在查询的表的内容一样。无副作用的代码在可读性和推理代码的能力方面非常出色。
如果您想更改值而不是创建新值,我会建议使用简单的 foreach
循环。这不是 LINQ 的设计目的。但是,我个人会尝试坚持使用不可变类型,使用 LINQ,并随时测量性能 - 我怀疑您会发现在很多情况下它并没有您想象的那么糟糕。
关于c# - 使用 LINQ 更新 IEnumerable 对象的简单方法,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/3930510/