gpt4 book ai didi

c# - 在不更改数据源的情况下过滤 DataGridView

转载 作者:IT王子 更新时间:2023-10-29 03:37:43 25 4
gpt4 key购买 nike

我正在使用 C# Visual Studio 2010 开发用户控件 - 一种用于过滤数据 GridView 的“快速查找”文本框。它应该适用于 3 种类型的 datagridview 数据源:DataTable、DataBinding 和 DataSet。我的问题是从显示在 DataGridView 上的 DataSet 对象中过滤 DataTable。

可能有 3 种情况(带有 DataGridView 和 TextBox 的标准 WinForm 应用程序的示例)- 前 2 种工作正常,我遇到了第 3 种问题:

<强>1。 datagridview.DataSource = dataTable :有效
所以我可以通过设置进行过滤:dataTable.DefaultView.RowFilter = "country LIKE '%s%'";

DataTable dt = new DataTable();

private void Form1_Load(object sender, EventArgs e)
{
dt.Columns.Add("id", typeof(int));
dt.Columns.Add("country", typeof(string));

dt.Rows.Add(new object[] { 1, "Belgium" });
dt.Rows.Add(new object[] { 2, "France" });
dt.Rows.Add(new object[] { 3, "Germany" });
dt.Rows.Add(new object[] { 4, "Spain" });
dt.Rows.Add(new object[] { 5, "Switzerland" });
dt.Rows.Add(new object[] { 6, "United Kingdom" });

dataGridView1.DataSource = dt;
}

private void textBox1_TextChanged(object sender, EventArgs e)
{
MessageBox.Show("DataSource type BEFORE = " + dataGridView1.DataSource.GetType().ToString());

dt.DefaultView.RowFilter = string.Format("country LIKE '%{0}%'", textBox1.Text);

MessageBox.Show("DataSource type AFTER = " + dataGridView1.DataSource.GetType().ToString());
}

<强>2。 datagridview.DataSource = bindingSource:有效
所以我可以通过设置进行过滤:bindingSource.Filter = "country LIKE '%s%'";

DataTable dt = new DataTable();
BindingSource bs = new BindingSource();

private void Form1_Load(object sender, EventArgs e)
{
dt.Columns.Add("id", typeof(int));
dt.Columns.Add("country", typeof(string));

dt.Rows.Add(new object[] { 1, "Belgium" });
dt.Rows.Add(new object[] { 2, "France" });
dt.Rows.Add(new object[] { 3, "Germany" });
dt.Rows.Add(new object[] { 4, "Spain" });
dt.Rows.Add(new object[] { 5, "Switzerland" });
dt.Rows.Add(new object[] { 6, "United Kingdom" });

bs.DataSource = dt;
dataGridView1.DataSource = bs;
}

private void textBox1_TextChanged(object sender, EventArgs e)
{
MessageBox.Show("DataSource type BEFORE = " + dataGridView1.DataSource.GetType().ToString());

bs.Filter = string.Format("country LIKE '%{0}%'", textBox1.Text);

MessageBox.Show("DataSource type AFTER = " + dataGridView1.DataSource.GetType().ToString());
}

<强>3。 datagridview.DataSource = 数据源; datagridview.DataMember = "TableName": 它不起作用
当您使用设计器设计表格时会发生这种情况:将工具箱中的 DataSet 放在表格上,将 dataTable 添加到其中,然后设置 datagridview.DataSource = dataSource;和 datagridview.DataMember = "TableName".
下面的代码假装这些操作:

DataSet ds = new DataSet();
DataTable dt = new DataTable();

private void Form1_Load(object sender, EventArgs e)
{
dt.Columns.Add("id", typeof(int));
dt.Columns.Add("country", typeof(string));

dt.Rows.Add(new object[] { 1, "Belgium" });
dt.Rows.Add(new object[] { 2, "France" });
dt.Rows.Add(new object[] { 3, "Germany" });
dt.Rows.Add(new object[] { 4, "Spain" });
dt.Rows.Add(new object[] { 5, "Switzerland" });
dt.Rows.Add(new object[] { 6, "United Kingdom" });

ds.Tables.Add(dt);
dataGridView1.DataSource = ds;
dataGridView1.DataMember = dt.TableName;
}

private void textBox1_TextChanged(object sender, EventArgs e)
{
MessageBox.Show("DataSource type BEFORE = " + dataGridView1.DataSource.GetType().ToString());
//it is not working
ds.Tables[0].DefaultView.RowFilter = string.Format("country LIKE '%{0}%'", textBox1.Text);

MessageBox.Show("DataSource type AFTER = " + dataGridView1.DataSource.GetType().ToString());
}

如果你测试它 - 虽然数据表被过滤(ds.Tables[0].DefaultView.Count 改变),但 datagridview 没有更新......我一直在寻找任何解决方案,但问题是 DataSource 无法更改 - 因为它是额外的控制,我不希望它弄乱程序员的代码。

我知道可能的解决方案是:
- 使用 DataBinding 从 DataSet 绑定(bind) DataTable 并将其用作示例 2:但这取决于程序员在编写代码时,
- 以编程方式将数据源更改为 BindingSource、dataGridView.DataSource = dataSet.Tables[0] 或更改为 DefaultView:但是,它会更改数据源。所以解决方案:

private void textBox1_TextChanged(object sender, EventArgs e)
{
MessageBox.Show("DataSource type BEFORE = " + dataGridView1.DataSource.GetType().ToString(), ds.Tables[0].DefaultView.Count.ToString());

DataView dv = ds.Tables[0].DefaultView;
dv.RowFilter = string.Format("country LIKE '%{0}%'", textBox1.Text);
dataGridView1.DataSource = dv;

MessageBox.Show("DataSource type AFTER = " + dataGridView1.DataSource.GetType().ToString(), ds.Tables[0].DefaultView.Count.ToString());
}

是 Not Acceptable ,正如您在 MessageBox 的数据源上看到的那样正在改变......

我不想那样做,因为程序员可能会写出类似这样的代码:

private void textBox1_TextChanged(object sender, EventArgs e)
{
MessageBox.Show("DataSource type BEFORE = " + dataGridView1.DataSource.GetType().ToString(), ds.Tables[0].DefaultView.Count.ToString());

DataSet dsTmp = (DataSet)(dataGridView1.DataSource); //<--- it is OK

DataView dv = ds.Tables[0].DefaultView;
dv.RowFilter = string.Format("country LIKE '%{0}%'", textBox1.Text);
dataGridView1.DataSource = dv; //<--- here the source is changeing from DataSet to DataView

MessageBox.Show("DataSource type AFTER = " + dataGridView1.DataSource.GetType().ToString(), ds.Tables[0].DefaultView.Count.ToString());

dsTmp = (DataSet)(dataGridView1.DataSource); //<-- throws an exception: Unable to cast object DataView to DataSet
}

他可以做到这一点,因为他在设计器中使用 DataSet 和 DataMember 设计了 ​​DataGridView。代码将被编译,但是,在使用过滤器后,它会抛出异常...

那么问题来了:如何在不将DataSource更改为另一个的情况下,过滤DataSet中的DataTable并将结果显示在DataGridView上?为什么我可以直接从示例 1 中过滤 DataTable,而从 DataSet 中过滤 DataTable 却不起作用?在那种情况下,也许它不是绑定(bind)到 DataGridView 的 DataTable?

请注意,我的问题来自设计问题,因此解决方案必须适用于示例 3。

最佳答案

我刚刚花了一个小时解决类似的问题。对我来说,答案简单得令人尴尬。

(dataGridViewFields.DataSource as DataTable).DefaultView.RowFilter = string.Format("Field = '{0}'", textBoxFilter.Text);

关于c# - 在不更改数据源的情况下过滤 DataGridView,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/5843537/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com