为什么这个LINQ查询只新建了内部List的一个实例?

时间:2015-03-02 22:01:18

标签: c# linq generics linq-to-sql

根据要求,我简化了这个问题。当尝试采用两个通用List并将它们混合时,我得到了意想不到的结果。

private List<ConditionGroup> GetConditionGroupParents()
{    
    return (from Conditions in dataContext.Conditions
               orderby Conditions.Name
               select new ConditionGroup
               {
                   GroupID = Conditions.ID,
                   GroupName = Conditions.Name,
/* PROBLEM */      MemberConditions = new List<Condition>()
               }).ToList();
}

private List<ConditionGroup> BuildConditionGroups()
{
    var results = GetConditionGroupParents();

    // contents of ConditionMaps is irrelevant to this matter
    List<ConditionMap> ConditionMaps = GenerateGroupMappings();

    // now pair entries from the map into their appropriate group,
    // adding them to the proper List<MemberConditions> as appropriate

    foreach (var map in ConditionMaps)
    {
        results.Find(groupId => groupId.GroupID == map.GroupID)
               .MemberConditions.Add(new ConditionOrphan(map));
    }

    return results;
}

我希望ConditionMaps中的每个映射都映射到“results.Find ....”语句中的单个ConditionGroup的MemberConditions。

相反,每个地图都会添加到每个组的列表中,并且会同时/同时发生。

[edit] I've since proven that there is only a single instance of 
       List<Memberconditions>, being referenced by each group.

       I unrolled the creation of the groups like so:

       .
       .
       .    
       /* PROBLEM */      MemberConditions = null }).ToList();

      foreach (var result in results)
      {
          List<Condition> memberConditions = new List<Condition>();
          results.MemberConditions = memberConditions;
      }

      return results;

      In that case I was able to watch each instantiation stepping 
      through the loop, and then it worked as expected.  My question 
      remains, though, why the original code only created a single 
      instance.  Thanks!
      .

为什么GetConditionGroupParents中的LINQ查询没有“新增”每个组的唯一MemberConditions列表,如上面的/ *问题* /注释中所示?

任何见解都表示赞赏。谢谢!

杰夫伍兹 阅读,PA

1 个答案:

答案 0 :(得分:0)

这是一个错误。作为解决方法,您可以创建工厂函数

static List<T> CreateList<T>(int dummy) { ... }

并根据当前行传递任何虚拟值,例如Conditions.ID

这个技巧很有效,因为与EF不同,L2S能够在查询的最后Select中调用不可翻译的函数。由于尚未实现此功能,您将无法迁移到EF。