You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

使用C# CurrencyManager AddNew()方法无法更新数据库记录求助

问题:使用C# CurrencyManager.AddNew()添加记录后数据库未更新

你遇到的问题是,通过CurrencyManager.AddNew()和EndCurrentEdit()虽然在内存的DataTable里创建了新记录,但这些变化并没有同步到实际的数据库中。下面是你的完整代码:

namespace currencyManager { 
    public partial class Form1 : Form { 
        public Form1() { InitializeComponent(); } 
        SqlConnection con; 
        SqlCommand cmd; 
        SqlDataAdapter da; 
        DataTable dt; 
        CurrencyManager cm; 

        private void Form1_Load(object sender, EventArgs e) { 
            con = new SqlConnection("data source=COUNTER16-PC,initial catalog=myDatabase;integrated security=true"); 
            con.Open(); 
            cmd = new SqlCommand("Select * from Students", con); 
            da = new SqlDataAdapter(); 
            da.SelectCommand = cmd; 
            dt = new DataTable(); 
            da.Fill(dt); 
            cm = (CurrencyManager)BindingContext[dt]; 

            txtID.DataBindings.Add("text",dt,"ID"); 
            txtFname.DataBindings.Add("text", dt, "FirstName"); 
            txtLname.DataBindings.Add("text", dt, "LASTNAME"); 
            txtState.DataBindings.Add("text", dt, "STATE"); 
            txtPhone.DataBindings.Add("text", dt, "PHONE"); 
            txtEmail.DataBindings.Add("text", dt, "EMAIL"); 
            txtGrade.DataBindings.Add("text", dt, "GRADEYEAR"); 
            txtGrade.DataBindings.Add("text", dt, "GPA"); 
            txtProgram.DataBindings.Add("text", dt, "PROGRAM"); 
            txtNews.DataBindings.Add("text", dt, "NEWLETTER"); 
        } 

        private void btn_first_Click(object sender, EventArgs e) { cm.Position = 0; } 
        private void btn_prev_Click(object sender, EventArgs e) { cm.Position--; } 
        private void btn_next_Click(object sender, EventArgs e) { cm.Position++; } 
        private void btn_last_Click(object sender, EventArgs e) { cm.Position = cm.Count - 1; } 

        private void btn_add_Click(object sender, EventArgs e) { cm.AddNew(); } 

        private void btn_save_Click(object sender, EventArgs e) { cm.EndCurrentEdit(); } 

        private void btn_update_Click(object sender, EventArgs e) { } 

        private void btn_delete_Click(object sender, EventArgs e) { cm.RemoveAt(cm.Position); } 
    } 
}
问题根源

CurrencyManager的操作只针对内存中的DataTable,而你使用的SqlDataAdapter默认只配置了SelectCommand用来查询数据,没有对应的InsertCommand、UpdateCommand和DeleteCommand来将DataTable的变更同步回数据库。你调用cm.EndCurrentEdit()只是确认了内存中数据的修改,但没有触发任何数据库写入操作。

解决方案

我们需要添加SqlCommandBuilder来自动生成所需的更新命令,然后在保存时调用SqlDataAdapter.Update()方法将变更提交到数据库。同时,建议优化数据库连接的管理(避免长期保持连接打开):

步骤1:添加SqlCommandBuilder自动生成更新命令

在Form1_Load方法中,创建SqlDataAdapter后,添加SqlCommandBuilder——它会根据你的SelectCommand自动生成对应的增删改命令:

da = new SqlDataAdapter(cmd); // 简化代码,直接把查询命令传入构造函数
SqlCommandBuilder cmdBuilder = new SqlCommandBuilder(da);

注意:SqlCommandBuilder要求查询的表必须有主键(比如你的ID字段),否则无法自动生成正确的更新命令,请确保Students表已设置主键。

步骤2:修改保存按钮的事件逻辑

更新btn_save_Click方法,在结束内存数据编辑后,调用da.Update(dt)把DataTable的变更同步到数据库:

private void btn_save_Click(object sender, EventArgs e) {
    cm.EndCurrentEdit();
    try {
        // 将DataTable的所有变更提交到数据库
        int rowsAffected = da.Update(dt);
        MessageBox.Show($"成功更新 {rowsAffected} 条记录");
    } catch (Exception ex) {
        MessageBox.Show($"保存失败:{ex.Message}");
    }
}

步骤3:优化数据库连接管理(可选但推荐)

避免长期保持数据库连接打开,用using语句管理连接,确保连接会被正确释放:

private void Form1_Load(object sender, EventArgs e) {
    string connectionString = "data source=COUNTER16-PC,initial catalog=myDatabase;integrated security=true";
    // using语句会自动释放连接资源
    using (SqlConnection con = new SqlConnection(connectionString)) {
        SqlCommand cmd = new SqlCommand("Select * from Students", con);
        da = new SqlDataAdapter(cmd);
        SqlCommandBuilder cmdBuilder = new SqlCommandBuilder(da);
        dt = new DataTable();
        da.Fill(dt); // Fill方法会自动打开/关闭连接(如果连接原本是关闭状态)
    }
    cm = (CurrencyManager)BindingContext[dt];
    // 控件绑定代码保持不变...
}

完整修改后的关键代码片段

SqlDataAdapter da; 
DataTable dt; 
CurrencyManager cm; 

private void Form1_Load(object sender, EventArgs e) {
    string connectionString = "data source=COUNTER16-PC,initial catalog=myDatabase;integrated security=true";
    using (SqlConnection con = new SqlConnection(connectionString)) {
        SqlCommand cmd = new SqlCommand("Select * from Students", con);
        da = new SqlDataAdapter(cmd);
        // 自动生成增删改命令
        SqlCommandBuilder cmdBuilder = new SqlCommandBuilder(da);
        dt = new DataTable();
        da.Fill(dt);
    }
    cm = (CurrencyManager)BindingContext[dt];
    // 控件绑定代码...
}

private void btn_save_Click(object sender, EventArgs e) {
    cm.EndCurrentEdit();
    try {
        int updatedRows = da.Update(dt);
        MessageBox.Show($"已成功保存 {updatedRows} 条记录到数据库");
    } catch (Exception ex) {
        MessageBox.Show($"保存出错:{ex.Message}");
    }
}

这样修改后,当你点击添加按钮创建新记录、输入内容后点击保存,数据就会正确同步到数据库中了。

内容的提问来源于stack exchange,提问作者Mehdi Sedaqat

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.05.29 08:41:14