Warning: file_get_contents(/data/phpspider/zhask/data//catemap/8/linq/3.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
C# 如何将多个linq查询组合到一个结果集中?_C#_Linq_Anonymous Types - Fatal编程技术网

C# 如何将多个linq查询组合到一个结果集中?

C# 如何将多个linq查询组合到一个结果集中?,c#,linq,anonymous-types,C#,Linq,Anonymous Types,我有一个多选复选框。根据选中的是哪一个,我想将结果合并到一个查询中。有点像: if (Checkbox1.Checked) { var query1 = from t in table1 ... } if (Checkbox2.Checked) { var query2 = from t in table2 ... } DataGridView1.DataSource = query1.Union(query2); // obviously doesnt // w

我有一个多选复选框。根据选中的是哪一个,我想将结果合并到一个查询中。有点像:

if (Checkbox1.Checked)
{
    var query1 = from t in table1 ...
}

if (Checkbox2.Checked)
{
    var query2 = from t in table2 ...
}

DataGridView1.DataSource = query1.Union(query2); // obviously doesnt
      // work since query1 and query2 are not defined in this scope.

您知道如何有选择地组合这些查询吗?

假设查询的类型相同,您可以在条件语句之外定义查询

首先,创建与参数类型相同的空枚举的helper方法:

static IEnumerable<T> CreateEmptyEnumerable<T>(IEnumerable<T> templateQuery)
{
    return Enumerable.Empty<T>();
}

这执行得很好,因为查询在枚举完之前不会实际执行,就像在对ToList的调用中一样。

如果不使用var而是使用已知类型,则可以通过初始化query1和query2


可枚举。如果复选框未被选中,则为空。

我只是在控制台应用程序中尝试了这一点,因为我很好奇,它刚刚起作用

class Program
{
    private class Data1
    {
        public int Code1 { get; set; }
        public string Value1 { get; set; }
    }

    private class Data2
    {
        public int Code2 { get; set; }
        public string Value2 { get; set; }
    }

    static void Main(string[] args)
    {
        var data1 = new[] { new Data1 { Code1 = 1, Value1 = "one" }, new Data1 { Code1 = 2, Value1 = "two" }, new Data1 { Code1 = 3, Value1 = "three" } };
        var data2 = new[] { new Data2 { Code2 = 101, Value2 = "aaa" }, new Data2 { Code2 = 102, Value2 = "bbb" }, new Data2 { Code2 = 103, Value2 = "ccc" } };

        var query1 = from d1 in data1 select new { code = d1.Code1, text = d1.Value1 };
        var query2 = from d2 in data2 select new { code = d2.Code2, text = d2.Value2 };

        var datasource = query1.Union(query2);

        foreach (var d in datasource)
        {
            Console.WriteLine(d);
        }
    }
}
但是,如果我将匿名类型中的字段名更改为不同的字段名,则会出现编译器错误,因此看起来关键在于匿名类型中的名称相同。或者将结果生成一个定义的类型:

使用,您可以执行以下操作:

public partial class _Default : System.Web.UI.Page
{
    IEnumerable<int> table1;
    IEnumerable<int> table2;

    protected void Page_Load(object sender, EventArgs e)
    {
        table1 = Enumerable.Range(0, 10);
        table2 = Enumerable.Range(10, 10);
    }

    protected void Button1_Click(object sender, EventArgs e)
    {
        var query = 
            Observable.If(() => CheckBox1.Checked,
                (from t in table1 select t).ToObservable(), Observable.Empty<int>())
            .Concat(
                Observable.If(() => CheckBox2.Checked,
                (from t in table2 select t).ToObservable(), Observable.Empty<int>())
            );

        query.Subscribe(i => Response.Write(i));
    }
}

您不能将null赋值给隐式类型的局部变量;我的回答基于这样一个前提:您的查询枚举匿名类型。如果不是,您可以用IEnumerable替换var。是的,它来自匿名类型。你的例子很接近,但仍然有一个问题。在第二个复选框中,如果finalQuery为null,则不能调用finalQuery.Unionquery2,因此需要另一个if语句.Man。这将教会我同时做两件事。我添加了一个helper函数,它可以让事情变得更干净——它返回一个空枚举,在本例中是指定查询的匿名枚举。所以,没有空检查了。嗯,我错过了问题是什么吗?!是的,我已经知道工会是有效的。问题是我的匿名类型是在if语句中声明的,这使得您不能在if语句之外进行联合。如果匿名类型相同,为什么不创建一个私有类并使用它呢?
public partial class _Default : System.Web.UI.Page
{
    IEnumerable<int> table1;
    IEnumerable<int> table2;

    protected void Page_Load(object sender, EventArgs e)
    {
        table1 = Enumerable.Range(0, 10);
        table2 = Enumerable.Range(10, 10);
    }

    protected void Button1_Click(object sender, EventArgs e)
    {
        var query = 
            Observable.If(() => CheckBox1.Checked,
                (from t in table1 select t).ToObservable(), Observable.Empty<int>())
            .Concat(
                Observable.If(() => CheckBox2.Checked,
                (from t in table2 select t).ToObservable(), Observable.Empty<int>())
            );

        query.Subscribe(i => Response.Write(i));
    }
}