我使用C#Winforms和SQL Server作为我的数据库。
在我的Combobox_Leave
事件中,它会使用前一个
Combobox
这是我的Combobox_Leave
事件之一,与其他Combobox
private void cmbPItem_Leave(object sender, EventArgs e)
{
using (SqlConnection conn = new SqlConnection(@"Server=" + ip + "," + port + "; Database=records; User ID=" + sqlid + "; Password=" + sqlpass + ""))
{
conn.Open();
using (SqlDataAdapter sda = new SqlDataAdapter(@"SELECT DISTINCT [Brand]
FROM [dbo].[products] WHERE Item LIKE '" + cmbPItem.Text + "'", conn))
{
DataTable dt = new DataTable();
sda.Fill(dt);
if (dt.Rows.Count != 0)
{
cmbPBrand.Items.Clear();
for (int b = 0; b < dt.Rows.Count; b++)
{
cmbPBrand.Items.Add(dt.Rows[b][0].ToString());
}
}
}
using (SqlDataAdapter sda = new SqlDataAdapter(@"SELECT DISTINCT [Manufacturer]
FROM [dbo].[products] WHERE Item LIKE '" + cmbPItem.Text + "'", conn))
{
DataTable dt = new DataTable();
sda.Fill(dt);
if (dt.Rows.Count != 0)
{
cmbPMan.Items.Clear();
for (int m = 0; m < dt.Rows.Count; m++)
{
cmbPMan.Items.Add(dt.Rows[m][0].ToString());
}
}
}
using (SqlDataAdapter sda = new SqlDataAdapter(@"SELECT DISTINCT [Car]
FROM [dbo].[products] WHERE Item LIKE '" + cmbPItem.Text + "'", conn))
{
DataTable dt = new DataTable();
sda.Fill(dt);
if (dt.Rows.Count != 0)
{
cmbPCar.Items.Clear();
for (int i = 0; i < dt.Rows.Count; i++)
{
cmbPCar.Items.Add(dt.Rows[i][0].ToString());
}
}
}
using (SqlDataAdapter sda = new SqlDataAdapter(@"SELECT DISTINCT [Year]
FROM [dbo].[products] WHERE Item LIKE '" + cmbPItem.Text + "'", conn))
{
DataTable dt = new DataTable();
sda.Fill(dt);
if (dt.Rows.Count != 0)
{
cmbPYr.Items.Clear();
for (int y = 0; y < dt.Rows.Count; y++)
{
cmbPYr.Items.Add(dt.Rows[y][0].ToString());
}
}
}
conn.Close();
}
}
输出就像这样
当用户点击第二个Combox
时,在此示例中为cmbPBrand
。它使用重复值填充Combobx
。但是,当用户点击另一个Combobox
时,不会从cmbPBrand
中选择任何条目。这些值不重复。
重复值的另一个例子。
在cmbPYr
中选择cmbPItem
后,点击DISTINCT
。它复制CLICK
值。
请注意,当用户Combobox
第二个Leave
时会发生这种情况。我正在为Combobox
使用MouseClick
个活动。
我还尝试添加MouseDown
和Enter
以及SelectedIndexChanged
和SELECT DISTINCT Brand,Manufacturer,Car,Year FROM [dbo].[products] WHERE Item LIKE 'BRAKE PADS'
事件。但它仍然重复这些值。
编辑:
使用查询时
BRAKE PADS
例如,cmbPItem.Text为ComboBox
。
它将查询近675行。
编辑:至于凯文的建议。此代码仅适用于品牌private void cmbProd_Enter(object sender, EventArgs e) {
itemValue(cmbPItem.Text); }
private void itemValue(string sitem) {
getBrand(sitem); }
private void getBrand(string sitem) {
using (SqlCommand cmd = new SqlCommand(@"SELECT DISTINCT [Brand] FROM [dbo].[products] WHERE Item = @Item"))
{
cmd.Parameters.Add(new SqlParameter("Item", sitem));
populateBrand(cmbPBrand, cmd);
} }
private void populateBrand(ComboBox cmb, SqlCommand cmd) {
using (SqlConnection conn = new SqlConnection(@"Server=" + ip + "," + port + "; Database=records; User ID=" + sqlid + "; Password=" + sqlpass + ""))
{
using (SqlDataAdapter sda = new SqlDataAdapter(cmd))
{
cmd.Connection = conn;
DataTable dt = new DataTable();
sda.Fill(dt);
if (dt.Rows.Count != 0)
{
cmb.Items.Clear();
for (int b = 0; b < dt.Rows.Count; b++)
{
cmb.Items.Add(dt.Rows[b][0].ToString());
}
}
conn.Close();
}
} }
,但仍显示重复值。
{{1}}
答案 0 :(得分:1)
我建议从稍微不同的角度解决问题。
首先,肯定应考虑更改要参数化的查询。就像我评论的那样,只要你将原始输入直接放入SQL语句中,就会打开SQL注入攻击的大门。即使它不是基于用户输入,它仍然是一个坏习惯进入。做SQL参数化并不难 - 这只是一行额外的代码。
接下来:重构您的代码。如果我理解正确,您的代码如下:
Event X
{
13 or so lines to update Combo Box #1
13 or so lines to update Combo Box #2
13 or so lines to update Combo Box #3
13 or so lines to update Combo Box #4
}
Event Y
{
13 or so lines to update Combo Box #1
13 or so lines to update Combo Box #2
13 or so lines to update Combo Box #3
13 or so lines to update Combo Box #4
}
Event Z
{
13 or so lines to update Combo Box #1
13 or so lines to update Combo Box #2
13 or so lines to update Combo Box #3
13 or so lines to update Combo Box #4
}
Event ... etc
使用单一责任原则(SRP)进行谷歌搜索并使用它 - 它将帮助您编写更清晰,更易于调试的代码。
什么时候说完了?然后你有一个很好的方法来弄清楚问题是什么:在你的“UpdateBrandCombo()”函数中添加一些调试行 - 在 only 的地方更新Brand组合框(现在,你有一个问题,那些事件中的任何一个都可能正在更新组合框,你真的没有任何好办法搞清楚它在做什么。)
类似的东西:
Event X
{
UpdateCombosWithSearch(cmbPItem.Text);
}
// ... later on ...
private void UpdateCombosWithSearch(string searchTerm)
{
UpdateBrandCombo(searchTerm);
UpdateMfgCombo(searchTerm);
UpdateCarCombo(searchTerm);
}
private void UpdateBrandCombo(string searchTerm)
{
SqlCommand sqlCmd = new SqlCommand("select distinct car from dbo.products where Item like @item");
sqlCmd.Parameters.Add(new SqlParameter("item", searchTerm));
SetComboBoxUsingQuery(cmbPBrand, sqlCmd);
}
private void SetComboBoxUsingQuery(ComboBox cbx, SqlCommand sqlCmd)
{
cbx.Items.Clear();
// code to get a DataTable from the sqlCmd
// code to read the DataTable and add items to cbx
}
看到美女?你没有重复的代码。您的事件都有一行:UpdateCombosWithSearch()。 UpdateCombosWithSearch只需在需要更新的每个组合框上调用Update。这些函数中的每一个都只生成一个SQL命令并传入哪个框进行更新。唯一具有任何SQL代码的函数是SetComboBoxUsingQuery()函数。
所以现在你可以添加如下内容:
System.Diagnostics.Debug.WriteLine("Event logged by " + (new System.Diagnostics.StackTrace()).ToString());
...其中一个功能 - 这样您就可以确定更新代码的调用位置/时间/方式。