【问题标题】:Check if a record already exists in SQL Server table before inserting在插入之前检查 SQL Server 表中是否已存在记录
【发布时间】:2021-08-18 22:19:45
【问题描述】:

我有一个包含 5 列和 3 行数据的 Excel 表。每次数据更改时,它都会上传到数据库。下面是我将数据从 Excel 表发送到 SQL Server 中现有表的代码。挑战在于,数据库接受唯一的 ID 值。如果您在 Excel 表中的 ID 已存在于数据库中时如何更改代码,我将不胜感激?代码以消息结束:

不允许重复!

Sub IMPORT()

    Dim con As ADODB.Connection
    Dim cmd As ADODB.Command

    Set con = New ADODB.Connection
    Set cmd = New ADODB.Command

    Dim r As Range

    con.ConnectionString = sqlconstr
    con.Open "Provider=sqloledb;Data Source=DS;Initial Catalog=AUTO;Integrated Security=SSPI"

    cmd.ActiveConnection = con

    For Each r In Range("a2", Range("a2").End(xlDown))

        If r.Offset(0, 4).Value <> "" Then

            cmd.CommandText = cmd.CommandText & _
            GetInsertText( _
                r.Offset(0, 0).Value, _
                r.Offset(0, 1).Value, _
                r.Offset(0, 2).Value, _
                r.Offset(0, 3).Value, _
                r.Offset(0, 4).Value _
            )

        End If

    Next r

    Debug.Print cmd.CommandText

    cmd.Execute

    con.Close
    Set con = Nothing

    msgbox "Import successful"

End Sub
Function GetInsertText(ID As String, Date1 As Date, Date2 As Date, Reference As String, Price As Double)

    sql = _
        "insert into dbo.TP (" & _
        "ID, Date1, Date2, Reference, Price)" & _
        "values (" & _
        "'" & ID & "'," & _
        "'" & Format(Date1, "yyyy-mm-dd") & "'," & _
        "'" & Format(Date2, "yyyy-mm-dd") & "'," & _
        "'" & Reference & "'," & _
        Replace(Format(Price, "#0.00"), ",", ".") & ");"

    GetInsertText = sql

End Function 

【问题讨论】:

  • @StureS 你能解释一下你为什么在这里发布谷歌搜索结果吗?
  • 一种方法是使用 SELECT 语句。如果记录存在,则执行 UPDATE,否则执行 INSERT。
  • @Dejan Dozet:谷歌搜索包含许多解决您问题的建议
  • 当然可以,但这也意味着我们可以在发帖之前回复任何人检查谷歌搜索,这不是一个好主意。让他们在这里问他们想问的任何问题,并尝试直接回答他们的问题。

标签: sql excel vba sql-insert


【解决方案1】:

我不确定语法是否正确,但您可以尝试以下方法:

Function ExistsAlready(ID As String, conn as Object) As Boolean

  Dim cmd As ADODB.Command

  Set cmd = New ADODB.Command

  cmd.CommandText = "select count(*) from dbo.TP where ID = '" & ID & "'"
  cmd.ActiveConnection = con
  Set rs = cmd.Execute

  ExistsAlready= rs.Fields(0).Value

End Function 

然后您可以使用它来检查您的表中是否已经存在 ID。

【讨论】:

    【解决方案2】:

    考虑使用ADO Command 支持的 ADO 参数化 MERGE,并避免在 VBA 字符串中串联 SQL。

    SQL (保存在下面的.sql文件中;注意?qmarks的使用)

    MERGE dbo.TP AS target  
    USING (VALUES (?, ?, ?, ?, ?)) 
          AS source(id, date1, date2, reference, price)
      
    ON (target.id = source.id)  
    WHEN MATCHED THEN
         UPDATE SET target.date1 = source.date1,
                    target.date2 = source.date2,
                    target.reference = source.reference,
                    target.price = source.price  
    WHEN NOT MATCHED THEN  
         INSERT (target.ID, 
                 target.Date1,
                 target.Date2,
                 target.Reference,
                 target.Price)  
         VALUES (source.ID,
                 source.Date1,
                 source.Date2, 
                 source.Reference,
                 source.Price); 
    

    VBA (读取 SQL 并绑定参数)

    Noe:以下是未经测试的代码,可能需要调整。调整参数值以与对应的 ADO DataTypeNum 对齐。

    Sub IMPORT()
        Dim con As ADODB.Connection, cmd As ADODB.Command
        Dim r As Range
    
        Set con = New ADODB.Connection
        Set cmd = New ADODB.Command
    
        con.ConnectionString = sqlconstr
        con.Open "Provider=sqloledb;Data Source=DS;Initial Catalog=AUTO;Integrated Security=SSPI"
    
        cmd.ActiveConnection = con
    
        ' READ SQL QUERY FROM FILE INTO STRING
        With CreateObject("Scripting.FileSystemObject")
            strSQL = .OpenTextFile("C:\path\to\my\SQL\Query.sql", 1).readall
        End With
    
        For Each r In Range("a2", Range("a2").End(xlDown))
            If r.Offset(0, 4).Value <> "" Then
                With cmd
                    .CommandText = cmd.CommandText & strSQL
                    
                    ' BIND PARAMETERS WITH ? IN SQL (ALIGN VALUES TO ad TYPES)
                    .Parameters.Append .CreateParameter("idparam", adVarChar, adParamInput, , r.Offset(0, 0).Value)
                    .Parameters.Append .CreateParameter("dt1param", adDate, adParamInput, , r.Offset(0, 1).Value)
                    .Parameters.Append .CreateParameter("dt2param", adDate, adParamInput, , r.Offset(0, 2).Value)
                    .Parameters.Append .CreateParameter("refparam", adVarChar, adParamInput, , r.Offset(0, 3).Value)
                    .Parameters.Append .CreateParameter("priceparam", adDecimal, adParamInput, , r.Offset(0, 4).Value)
                End With
            End If
        Next r
    
        cmd.Execute
    
        cmd.close: con.Close
        Set cmd = Nothing: Set con = Nothing
    
        Msgbox "Import successful"
    End Sub
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2012-03-06
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2014-01-19
      • 2010-11-25
      相关资源
      最近更新 更多