IEnumerable 中第一项的变量分配不起作用
Variable assignment to first item in IEnumerable does not work
我正在尝试将值 true
分配给我的对象集合中的一个字段。我正在使用 First()
方法检索第一个对象,并分配给它。在此示例中,我将值 true
分配给 Show
变量。但是,在赋值之后,Show
变量似乎仍然是 false
:
public class CallerItem
{
public int IndexId;
public string PhoneNumber;
public bool ToInd;
public bool Show;
}
public void myFunc() {
var callers = dbCallerRecs.Select(x => new CallerItem() { IndexId = x.IndexId, PhoneNumber = x.PhoneNumber, ToInd = x.ToInd });
var toCallers = callers.Where(x => x.ToInd);
if (toCallers.Any())
{
toCallers.First().Show = true;
Console.Log(toCallers.First().Show); //THIS LOGS 'false'. HOWEVER, IT SHOULD LOG 'true'
}
}
有什么我想念的吗?也许我对Where
子句返回的引用的理解不对?
var callers = dbCallerRecs.Select(x => new CallerItem() { IndexId = x.IndexId, PhoneNumber = x.PhoneNumber, ToInd = x.ToInd });
var toCallers = callers.Where(x => x.ToInd);
定义一个查询,当结果 IEnumerable<CallerItem>
(或实现 IEnumerable<CallerItem>
的 IQueryable<CallerItem>
)中的某些元素被迭代时,该查询将被评估。这在您的代码中发生了三次 - 在调用 Any
时和两次调用 First
时(假设 .Any()
returns true
)。
您看到此行为的原因是对 First
的两次调用导致重新评估查询并为每次调用创建一个新对象,因此您正在修改一个不同的对象你最终记录。
一种解决方案是急切地评估查询:
var toCallers = callers.Where(x => x.ToInd).ToList();
if (toCallers.Any())
{
toCallers.First().Show = true;
Console.Log(toCallers.First().Show); //THIS LOGS 'false'. HOWEVER, IT SHOULD LOG 'true'
}
每次调用 .First()
你都是 getting the first item。对于某些可枚举对象(例如 IQueryable
),它每次都会 return 一个 不同的 对象。
下面的代码将只调用一次方法,从而避免了这个问题。 另请注意,我使用了 FirstOrDefault
而不是 Any
then First
- 因为前者会导致更少的数据库查询(即更快)。
var caller = toCallers.FirstOrDefault().
if (caller != null)
{
caller.Show = true;
Console.Log(caller.Show);
}
我正在尝试将值 true
分配给我的对象集合中的一个字段。我正在使用 First()
方法检索第一个对象,并分配给它。在此示例中,我将值 true
分配给 Show
变量。但是,在赋值之后,Show
变量似乎仍然是 false
:
public class CallerItem
{
public int IndexId;
public string PhoneNumber;
public bool ToInd;
public bool Show;
}
public void myFunc() {
var callers = dbCallerRecs.Select(x => new CallerItem() { IndexId = x.IndexId, PhoneNumber = x.PhoneNumber, ToInd = x.ToInd });
var toCallers = callers.Where(x => x.ToInd);
if (toCallers.Any())
{
toCallers.First().Show = true;
Console.Log(toCallers.First().Show); //THIS LOGS 'false'. HOWEVER, IT SHOULD LOG 'true'
}
}
有什么我想念的吗?也许我对Where
子句返回的引用的理解不对?
var callers = dbCallerRecs.Select(x => new CallerItem() { IndexId = x.IndexId, PhoneNumber = x.PhoneNumber, ToInd = x.ToInd });
var toCallers = callers.Where(x => x.ToInd);
定义一个查询,当结果 IEnumerable<CallerItem>
(或实现 IEnumerable<CallerItem>
的 IQueryable<CallerItem>
)中的某些元素被迭代时,该查询将被评估。这在您的代码中发生了三次 - 在调用 Any
时和两次调用 First
时(假设 .Any()
returns true
)。
您看到此行为的原因是对 First
的两次调用导致重新评估查询并为每次调用创建一个新对象,因此您正在修改一个不同的对象你最终记录。
一种解决方案是急切地评估查询:
var toCallers = callers.Where(x => x.ToInd).ToList();
if (toCallers.Any())
{
toCallers.First().Show = true;
Console.Log(toCallers.First().Show); //THIS LOGS 'false'. HOWEVER, IT SHOULD LOG 'true'
}
每次调用 .First()
你都是 getting the first item。对于某些可枚举对象(例如 IQueryable
),它每次都会 return 一个 不同的 对象。
下面的代码将只调用一次方法,从而避免了这个问题。 另请注意,我使用了 FirstOrDefault
而不是 Any
then First
- 因为前者会导致更少的数据库查询(即更快)。
var caller = toCallers.FirstOrDefault().
if (caller != null)
{
caller.Show = true;
Console.Log(caller.Show);
}