0

私は何か奇妙なことに遭遇しました.なぜそれがこのように振る舞っているのか正確にはわかりません. for each ループで、相互参照のためにテーブルに行を追加しています。次のコードを使用します。

For Each cp In pCheckPoints
    If cp <> String.Empty Then
        Dim insertSQL As New StringBuilder
        With insertSQL
            .Append("INSERT INTO [CheckpointMessage] ( ")
            .Append(" [MessageID] ")
            .Append(", [CheckPoint] ")
            .Append(" ) VALUES ( ")
            .Append(" @MessageID ")
            .Append(", @Checkpoint ")
            .Append(" ) ")
        End With
        Using objCommand As New SqlCommand(insertSQL.ToString, MySQLConnection)
            With objCommand.Parameters
                .AddWithValue("@MessageID", pMessageID)
                .AddWithValue("@Checkpoint", cp)
            End With
            objCommand.ExecuteNonQuery()
            objCommand.CommandText = String.Empty
        End Using
    End If
Next

objCommand.CommandText = String.Empty 行がないと、CommandText は insertSQL を追加していますが、それは私には意味がありません。なぜなら、objCommand の commandText は using ブロックにあるため空であると予想されるからです。

4

2 に答える 2

3

コマンドテキストは毎回同じです。再構築しないでください。これを試して:

Dim insertSql As String = _
    "INSERT INTO [CheckpointMessage] " & _
        "([MessageID], [CheckPoint]) " & _
        "VALUES " & _
        "(@MessageID, @ChceckPoint)"

Using cmd As New SqlCommand(insertSql, MySQLConnection)
    cmd.Parameters.Add("@MessageID", SqlDbType.Int).Value = pMessageID
    cmd.Parameters.Add("@CheckPoint", SqlDbType.NVarChar, 255) ''# I had to guess at this type

    For Each cp As String In pCheckPoints.Where(Function(c) Not String.IsNullOrEmpty(c))
        cmd.Parameters("@CheckPoint").Value = cp
        cmd.ExecuteNonQuery()
    Next cp
End Using

多くの理由で優れています。

  • コンパイラーは、StringBuilder が実行時にその作業を強制した場合に、文字列の連結を最適化して取り除くことができます。
  • 明示的に型指定されたパラメーターは、SQL Server のパフォーマンスを実際に低下させたり、クエリを中断させたりする可能性のあるいくつかのエッジ ケースを回避します。
  • これにより、チェックポイントごとに1ではなく、挿入クエリ文字列が1回だけ作成されます
  • これにより、1 つの SqlCommand オブジェクトのみが作成されます
于 2010-03-03T15:06:27.377 に答える
0

元の質問以外に、次の行をループにする必要はありません

Dim insertSQL As New StringBuilder

        With insertSQL
            .Append("INSERT INTO [CheckpointMessage] ( ")
            .Append(" [MessageID] ")
            .Append(", [CheckPoint] ")
            .Append(" ) VALUES ( ")
            .Append(" @MessageID ")
            .Append(", @Checkpoint ")
            .Append(" ) ")
        End With

        Using objCommand As New SqlCommand(insertSQL.ToString, MySQLConnection)

文字列を一度使用して、パラメーター化されたクエリでコマンドを作成objCommandし、ループで同じインスタンスを使用できます。ループに属するのは動的な値だけです。

于 2010-03-03T15:05:36.240 に答える