【问题标题】:Is it possible to add two IQueryable's together?是否可以将两个 IQueryable 添加在一起?
【发布时间】:2011-03-30 09:01:49
【问题描述】:

我一直在 IQueryable(具有相同类型)上使用 Union 来尝试从两个集合中生成一个集合,但它不起作用。我相信我对 IQueryable 成员的理解是错误的。

我想我可以使用 union 方法(在 foreach 中)构建一个 SQL 语句,该语句将执行如下操作:

SELECT * FROM MYTABLE WHERE FK = 1
UNION
SELECT * FROM MYTABLE WHERE FK = 9
UNION
SELECT * FROM MYTABLE WHERE FK = 15

以前我认为必须有一个可用的方法,它在两个 IQueryable 上产生与旧的最喜欢的 ArrayList 的 AddRange 相同的效果,这确实是我在这里尝试实现的基础。

【问题讨论】:

    标签: collections arraylist generics iqueryable


    【解决方案1】:

    实际上,这完全符合预期:

    var q1 = from c in db.Customers where c.CustomerID.StartsWith("A") select c;
    var q2 = from c in db.Customers where c.CustomerID.StartsWith("B") select c;
    var q3 = from c in db.Customers where c.CustomerID.StartsWith("C") select c;
    
    var q4 = q1.Union(q2).Union(q3);
    

    (我使用的是 Northwind 数据库)。它会生成一条 SQL 语句,将三个查询联合起来。

    更新:我想我误解了你所说的“循环”的意思。这工作正常:)

    static void Main(string[] args)
    {
        var db = new NorthwindDataContext();
        IQueryable<Customer> query = from c in db.Customers 
                                     where c.CustomerID.StartsWith("A") 
                                     select c;
    
        foreach (var ch in "EIOV")
        {
            var chh = ch.ToString();  // separate variable so closure work right
    
            query = query.Union(from c in db.Customers 
                                where c.CustomerID.StartsWith(chh) 
                                select c);
        }
    
        foreach (var c in query)
        {
            Console.WriteLine(c.CompanyName);
        }
    }
    

    【讨论】:

    • foreach(var c in q4) 应该可以工作,但如果不是foreach(var c in q4.ToList()) 可以。
    • 但它是否适用于删除已知 q1、q2、q4 等数量的循环。如果 qN 是 2000 的循环怎么办?每次迭代似乎都会覆盖前一次迭代的 LINQ 语句,因为它们共享用于构建查询的 var。
    • @JamesCurran 我发现了另一种情况:如果 q1 为空,则 q4 为空,因为没有什么可以合并的。我遇到了这个问题。请帮忙,谢谢。
    【解决方案2】:

    我终于通过使用 List 并简单地调用 AddRange() 解决了这个问题。列表完成后,我调用 list.AsQueryable() 来获取 IQueryable 集合。

    这是最好的方法吗? 这将为列表中的每个添加创建一个 SQL 调用 - 有没有办法创建正确的 UNION 语句?

    【讨论】:

      【解决方案3】:

      IQueryable.Concat() 会是您要找的吗?

      【讨论】:

      • 恐怕没有什么不同。您能否提供一个在 foreach 中使用的示例?
      【解决方案4】:

      你可以试试这样的:

      var qry = 
      new [] {
          "one", "two", "three", "four"
      }
      .Select(z=>MyTable.Where(x=>x.Number==z))
      .Aggregate((a,x)=>a.Union(x))
      .ToList();
      

      这样做是创建一个 IQueryable,然后您可以将其具体化(请参阅 ToList())以生成单个服务器端语句。

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        相关资源
        最近更新 更多