在我的mysql表中,我看起来像这个
ControlNum|Title |NumOfEpis|Description|
001 |naruto |500 |some text |
002 |conan |700 |some text |
现在,我在C#中进行了一个用户控件,其中允许用户更新所有列,除了主要的" ControlNum"。因此,假设每列在上述用户控件中都有自己的文本框,以免在标题列中重复,例如用户编辑第2行标题并将其放置为"火影忍者",也将被重复。此方法称为checkdata();
void checkData()
{
SuspendLayout();
try
{
MySqlConnection conn = new MySqlConnection(myConnection);
conn.Open();
MySqlCommand command = new MySqlCommand("SELECT * FROM maindatabase.animelist where TitleAnime=?Title;", conn);
//command.Parameters.AddWithValue("?CN", int.Parse(a.ToString()));
command.Parameters.AddWithValue("?Title", textBox3.Text);
MySqlDataReader reader = command.ExecuteReader();
int ctr = 0;
while (reader.Read())
{
ctr++;
}
if (ctr == 1)
{
my = Form.ActiveForm as MyList;
my.msg = new Message_Box();
my.msg.Descrip.Text = "Record is already in the Database";
my.msg.Title.Text = "Duplicate Record";
my.msg.ShowDialog();
}
else
{
updateData();
}
conn.Close();
ResumeLayout();
}
catch (Exception ex)
{
MessageBox.Show("" + ex);
}
}
它在起作用,但我的问题是,如果用户只更新EPIS和描述的数量,并且不打算真正更新标题,我的方法仍然检测到有重复的内容,因为我的逻辑是"如果我的逻辑是"(ctr == 1)" ..我想我错过了某种方法,或者我在这里使用错误的方法。>
如果您的应用程序支持多个用户,您需要确保在您的检查重复项和数据库更新之间不会进行更改。
最简单的方法是按照Mbeckish的建议,对标题列创建独特的约束:
ALTER TABLE maindatabase.animelist
ADD CONSTRAINT U_animelist_TitleAnime UNIQUE (TitleAnime)
数据库引擎将执行唯一的标题,您的客户可以通过捕获任何约束违规例外来处理用户反馈:
void checkData()
{
SuspendLayout();
try
{
updateData();
}
catch (Exception ex)
{
MySqlException sqlEx = ex as MySqlExecption;
// If there is a constraint violation error.
// (I may have the wrong error number, please test.)
if (sqlEx != null && sqlEx.Number == 1062)
{
my = Form.ActiveForm as MyList;
my.msg = new Message_Box();
my.msg.Descrip.Text = "Record is already in the Database";
my.msg.Title.Text = "Duplicate Record";
my.msg.ShowDialog();
}
else
{
MessageBox.Show("" + ex);
}
}
finally
{
ResumeLayout();
}
}
您不想拥有两个具有相同内容的标题。通过该列上的唯一索引可以自动实现这一点。但是,如果您不想为此添加索引,则可以将查询更改为
SELECT ControlNum FROM maindatabase.animelist
WHERE TitleAnime=?Title;
然后您的逻辑还应检查控制num是否有差异
int currentNum = int.Parse(a.ToString()));
while (reader.Read())
{
int ctrlNum = reader.GetInt32(0);
if(ctrlNum != currentNum)
ctr++;
}
if (ctr > 0)
......
这样,只有当检索到的控制名称与您在接口中选择的controlnum不同时,您才会增加计数器
。另一种方法是以下方法(请参阅下面的@mbeckish评论)
SELECT 1 FROM maindatabase.animelist
WHERE TitleAnime=?Title AND ControlNum <> ?CN
command.Parameters.AddWithValue("?CN", int.Parse(a.ToString()));
command.Parameters.AddWithValue("?Title", textBox3.Text);
object result = command.ExecuteScalar();
if(result != null)
{
// Found a record with different ControlNum but with the same title
// Error here
}
这可能比第一个优于第一个优点,因为您不需要循环,并且可以使用更简单,更具性能的executesCalar,该尺度仅返回第一行的第一列(在这种情况下为1)而无需构建mySqlDatareAder对象
更改副本查找SQL:
SELECT MAX(Title) as Count
FROM maindatabase.animelist
GROUP BY Title , NumOfEpis, Description
如果计数> 1,则有一个重复。