条件 SQL 语句 - 在插入/更新查询之间切换 [重复]

Posted

技术标签:

【中文标题】条件 SQL 语句 - 在插入/更新查询之间切换 [重复]【英文标题】:Conditional SQL statement - switching between insert/update query [duplicate] 【发布时间】:2013-12-13 08:49:40 【问题描述】:

有没有办法在此处将 if/else 子句插入以下行:

command.CommandText = "UPDATE Table1 SET ID=value1,Team=value2 WHERE ID=value3";

如果可以找到 ID=value3(换句话说,该行已经存在),则会进行更新查询,但在找不到的情况下,我希望进行插入查询:

command.CommandText = "INSERT INTO Table1 (ID,Team) VALUES (value1,value2)";

发生...我该怎么做?

private void button1_Click(object sender, EventArgs e)

    // save to access database when user clicks on the save button
    using (OleDbConnection conn = new OleDbConnection())
    
        //the file path of mdb
        string filepath = @"C:\Users\sy\Visual Studio 2008\Projects\demo\demo\CE_Database.mdb";
        conn.ConnectionString = "Provider=Microsoft.Jet.OLEDB.4.0;data source=" + filepath + ";";
        OleDbCommand command = new OleDbCommand();
        command.Connection = conn;
        //your update satemenet
        command.CommandText = "UPDATE Table1 SET ID=value1,Team=value2 WHERE ID=value3";
        conn.Open();
        //update to ms access
        command.ExecuteNonQuery();
        conn.Close();
    

【问题讨论】:

如何知道该行是否存在?您是否查询数据库,以便在某个时候拥有 Id? NB 您不必在 using 块内显式关闭连接。 @ZevSpitz:真的吗?参考? @methuselah - 你检查过 sqlservers MERGE 吗? 由于 MS Access 不支持“upsert”,请检查此解决方案:***.com/a/6200623/3098069 【参考方案1】:

由于command.ExecuteNonQuery();会返回受影响的行数,你可以检查update命令返回的内容,如果记录不存在该方法将返回0,那么你可以继续插入方法:

private string filepath = @"C:\Users\sy\Visual Studio 2008\Projects\demo\demo\CE_Database.mdb";
private string connectionString = "Provider=Microsoft.Jet.OLEDB.4.0;data source=" + filepath + ";";

private void button1_Click(object sender, EventArgs e)
       
    if (this.Update() == 0)
    
        this.Insert();
    


private int Update()
   
    using (OleDbConnection conn = new OleDbConnection(connectionString))
    using (OleDbCommand command = new OleDbCommand("UPDATE Table1 SET ID=value1,Team=value2 WHERE ID=value3", conn);
    
        conn.Open();
        return command.ExecuteNonQuery();
    

private int Insert()
       
    using (OleDbConnection conn = new OleDbConnection(connectionString))
    using (OleDbCommand command = new OleDbCommand("INSERT INTO Table1 (ID,Team) VALUES (value1,value2)", conn);
    
        conn.Open();
        return command.ExecuteNonQuery();
    


要清除 cmets 的答案,OleDbConnection.Dispose() 方法如下所示:

protected override void Dispose(bool disposing)

    if (disposing)
    
        this._userConnectionOptions = null;
        this._poolGroup = null;
        this.Close();
    
    this.DisposeMe(disposing);
    base.Dispose(disposing);

所以连接会被 Dispose 方法关闭,所以当你的连接在 using 块时,不需要显式调用Close()

【讨论】:

比我的回答更好的文章:>【参考方案2】:

听起来您在使用 MERGE 语句...在 JET 版本的 SQL 中不存在。不过,这适用于大多数事情:

UPDATE Table1 RIGHT JOIN Table2
ON Table1.[KeyField] = Table2.[KeyField]
SET Table1.[KeyField] = Table2.[KeyField],
Table1.[OtherField] = Table2.[OtherField]

如果它在Table2 中,它将被插入到Table1,如果它已经在Table1 中,则覆盖值(更新)。

【讨论】:

【参考方案3】:

这很简单。在运行INSERTUPDATE 之前,通过SELECT COUNT(*) 查询检查是否存在ID = 3。

【讨论】:

【参考方案4】:

您可以先使用 ExecuteNonQuery() 执行 UPDATE 查询,它会返回受影响的行数。

如果受影响的行数为 0,那么您将运行 INSERT 查询。

            //the file path of mdb
            string filepath = @"C:\Users\sy\Visual Studio 2008\Projects\demo\demo\CE_Database.mdb";
            conn.ConnectionString = "Provider=Microsoft.Jet.OLEDB.4.0;data source=" + filepath + ";";
            OleDbCommand command = new OleDbCommand();
            command.Connection = conn;
            //your update satemenet
            command.CommandText = "UPDATE Table1 SET ID=value1,Team=value2 WHERE ID=value3;";
            conn.Open();
            //update to ms access
            int affectedRows = command.ExecuteNonQuery(); // returns 1 if the row exist, 0 if it does not.

            if (affectedRows == 0)
            
                  command.CommandText = "INSERT INTO Table1 (ID,Team) VALUES (value1,value2)";
                  command.ExecuteNonQuery(); // perform insert
            

            conn.Close()

编辑:正如 Gord Thompson 指出的那样,最初的解决方案不起作用。使用“UPDATE .....; SELECT @@ROWCOUNT”执行Scalar()。将此更改为使用 ExecuteNonQuery,并从该方法获取受影响的行数。

使用@@ROWCOUNT 的旧解决方案:

            command.CommandText = "UPDATE Table1 SET ID=value1,Team=value2 WHERE ID=value3; SELECT @@ROWCOUNT;";
            conn.Open();
            //update to ms access
            int affectedRows = (int)command.ExecuteScalar(); // returns 1 if the row exist, 0 if it does not.

            if (affectedRows == 0)
            
                  command.CommandText = "INSERT INTO Table1 (ID,Team) VALUES (value1,value2)";
                  command.ExecuteNonQuery(); // perform insert
            

【讨论】:

不好。我将进行编辑,使其使用 Executenonquery(),并删除 @@rowcount。 :)【参考方案5】:

使用@@ROWCOUNT

command.CommandText = "UPDATE Table1 SET ID=value1,Team=value2 WHERE ID=value3 IF @@ROWCOUNT = 0 INSERT INTO Table1 (ID,Team) VALUES (value1,value2)"

编辑:正如 Gord 所说,这行不通,我太快了,没有注意到它是 Access。

This 是一个类似的问题和解决方案。

【讨论】:

这在 Access 中不起作用。

以上是关于条件 SQL 语句 - 在插入/更新查询之间切换 [重复]的主要内容,如果未能解决你的问题,请参考以下文章

用sql语句更新一条记录,如果不存在就插入,怎么写?

SQL 基础语句

sqlserver的查询语句和插入更新语句怎么用

当条件匹配新插入的记录时,T-Sql MERGE 语句更新

SQL Server 触发器切换插入、删除、更新

SQL语句中怎样循环插入规律数据啊??