[英]LINQ: dynamic Where clause with toggle the combination of cases
我有一个绑定到angridview的列表,我希望能够“动态”创建过滤器Where子句,同时由用户控制过滤器选项的组合。
按模型布尔属性过滤原始列表的最佳方法是什么,并允许切换过滤器的每个条件?
我知道filterdList不是nececery,但我已经看过的其他解决方案都不允许切换Where子句的条件。
public partial class Form1 : Form
{
List<dummy> Origlist = new List<dummy> {
new dummy { pk = 1 , istype1 = true, istype2 = false, istype3=false, istype4=false },
new dummy { pk = 2 , istype1 = true, istype2 = false, istype3=false, istype4=false },
new dummy { pk = 3 , istype1 = false, istype2 = true, istype3=false, istype4=false },
new dummy { pk = 4 , istype1 = false, istype2 = true, istype3=false, istype4=false },
new dummy { pk = 5 , istype1 = false, istype2 = false, istype3=true, istype4=false },
new dummy { pk = 6 , istype1 = false, istype2 = false, istype3=true, istype4=false },
new dummy { pk = 7 , istype1 = false, istype2 = false, istype3=false, istype4=true },
new dummy { pk = 8 , istype1 = false, istype2 = false, istype3=false, istype4=true },
new dummy { pk = 9 , istype1 = false, istype2 = false, istype3=true, istype4=false },
new dummy { pk = 10 , istype1 = false, istype2 = true, istype3=false, istype4=false },
new dummy { pk = 11 , istype1 = false, istype2 = false, istype3=false, istype4=false }
};
List<dummy> filteredList = new List<dummy>();
public Form1()
{
InitializeComponent();
}
private void Bind()
{
dataGridView1.DataSource = null;
dataGridView1.DataSource = filteredList;
}
private void checkBox1_CheckedChanged(object sender, EventArgs e)
{
if (checkBox1.Checked)
{
filteredList.AddRange(Origlist.Where(a => a.istype1 == true).ToList());
}
else
{
filteredList.RemoveAll(a => a.istype1 == true);
}
Bind();
}
private void checkBox2_CheckedChanged(object sender, EventArgs e)
{
if (checkBox2.Checked)
{
filteredList.AddRange(Origlist.Where(a => a.istype2 == true).ToList());
}
else
{
filteredList.RemoveAll(a => a.istype2 == true);
}
Bind();
}
private void checkBox3_CheckedChanged(object sender, EventArgs e)
{
if (checkBox3.Checked)
{
filteredList.AddRange(Origlist.Where(a => a.istype3 == true).ToList());
}
else
{
filteredList.RemoveAll(a => a.istype3 == true);
}
Bind();
}
private void checkBox4_CheckedChanged(object sender, EventArgs e)
{
if (checkBox4.Checked)
{
filteredList.AddRange(Origlist.Where(a => a.istype4 == true).ToList());
}
else
{
filteredList.RemoveAll(a => a.istype4 == true);
}
Bind();
}
}
尝试这样的事情(未经测试):
public partial class Form1 : Form
{
List<dummy> Origlist = new List<dummy> {
new dummy { pk = 1 , istype1 = true, istype2 = false, istype3=false, istype4=false },
new dummy { pk = 2 , istype1 = true, istype2 = false, istype3=false, istype4=false },
new dummy { pk = 3 , istype1 = false, istype2 = true, istype3=false, istype4=false },
new dummy { pk = 4 , istype1 = false, istype2 = true, istype3=false, istype4=false },
new dummy { pk = 5 , istype1 = false, istype2 = false, istype3=true, istype4=false },
new dummy { pk = 6 , istype1 = false, istype2 = false, istype3=true, istype4=false },
new dummy { pk = 7 , istype1 = false, istype2 = false, istype3=false, istype4=true },
new dummy { pk = 8 , istype1 = false, istype2 = false, istype3=false, istype4=true },
new dummy { pk = 9 , istype1 = false, istype2 = false, istype3=true, istype4=false },
new dummy { pk = 10 , istype1 = false, istype2 = true, istype3=false, istype4=false },
new dummy { pk = 11 , istype1 = false, istype2 = false, istype3=false, istype4=false }
};
Options options = new Options();
private class Options {
public bool istype1 { get; set; }
public bool istype2 { get; set; }
public bool istype3 { get; set; }
public bool istype4 { get; set; }
}
public Form1()
{
InitializeComponent();
}
private void Bind()
{
dataGridView1.DataSource = null;
dataGridView1.DataSource = OrigList.Where(a =>
(options.istype1 && a.istype1) ||
(options.istype2 && a.istype2) ||
(options.istype3 && a.istype3) ||
(options.istype4 && a.istype4)
).ToList();
}
private void checkBox1_CheckedChanged(object sender, EventArgs e)
{
options.istype1 = checkBox1.checked;
Bind();
}
private void checkBox2_CheckedChanged(object sender, EventArgs e)
{
options.istype2 = checkBox2.checked;
Bind();
}
private void checkBox3_CheckedChanged(object sender, EventArgs e)
{
options.istype3 = checkBox3.checked;
Bind();
}
private void checkBox4_CheckedChanged(object sender, EventArgs e)
{
options.istype4 = checkBox4.checked;
Bind();
}
}
还有其他方法可以减少重复,但这是一个开始。
我想说最简单/最干净的方法是使用ADO.NET DataSet来处理你的数据,而不是使用一堆带有一些Linq查询的List。 ADO.NET DataSet是官方的Winforms生活方式 。
您可以将这些数据集/数据表与BindingSource组件一起用作DataGridView的DataSource,并使用BindingSource的Filter String属性。 这个String表达式可以通过一些If子句轻松构建,这些子句按照MSND DataColumn表达式语法测试CheckBox的状态和字符串连接。
还有一些其他干净的方法,比如使用IBindingListView接口的部分实现来扩展BindingList类。 但这是一些相当困难的东西,特别是当你知道微软已经为你为DataSet做了这项工作时...如果你不害怕,这篇文章是一个很好的起点。
可以为每个CheckBox重用单个事件处理程序,并且该事件处理程序可以将每个属性与相应的CheckBox进行比较。
List<dummy> Origlist = new List<dummy>
{
new dummy { pk = 1 , istype1 = true, istype2 = false, istype3=false, istype4=false },
new dummy { pk = 2 , istype1 = true, istype2 = false, istype3=false, istype4=false },
new dummy { pk = 3 , istype1 = false, istype2 = true, istype3=false, istype4=false },
new dummy { pk = 4 , istype1 = false, istype2 = true, istype3=false, istype4=false },
new dummy { pk = 5 , istype1 = false, istype2 = false, istype3=true, istype4=false },
new dummy { pk = 6 , istype1 = false, istype2 = false, istype3=true, istype4=false },
new dummy { pk = 7 , istype1 = false, istype2 = false, istype3=false, istype4=true },
new dummy { pk = 8 , istype1 = false, istype2 = false, istype3=false, istype4=true },
new dummy { pk = 9 , istype1 = false, istype2 = false, istype3=true, istype4=false },
new dummy { pk = 10 , istype1 = false, istype2 = true, istype3=false, istype4=false },
new dummy { pk = 11 , istype1 = false, istype2 = false, istype3=false, istype4=false }
};
public Form1()
{
InitializeComponent();
}
private void checkBox_CheckedChanged(object sender, EventArgs e)
{
dataGridView1.DataSource = Origlist.Where(a =>
a.istype1 == checkBox1.Checked &&
a.istype2 == checkBox2.Checked &&
a.istype3 == checkBox3.Checked &&
a.istype4 == checkBox4.Checked).ToList();
}
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.