ExecuteNonQuery命令中缺少参数,在VB.NET和Access中使用

时间:2012-11-23 20:06:33

标签: sql vb.net ms-access-2007 oledb

我在Access 2007中有一个非常简单的数据库,我使用VB 2010连接到它。有两个表,MenuItems和Orders,Orders.orderDate的类型为“Date”。

我在我的一个VB表单中运行以下代码(连接字符串,其他一切都很好):

  sql = "SELECT OrderDate, MenuItem FROM MenuItems, Orders WHERE Orders.itemID = MenuItem.ID AND Orders.orderDate BETWEEN '" + fromDate + "' AND '" + toDate + "'"
  Dim cmd As New OleDb.OleDbCommand(sql, con)
  Dim count As Integer = cmd.ExecuteNonQuery()

但我得到一个错误:

System.Data.OleDb.OleDbException (0x80040E10): value wan't given for one or more of the required parameters

似乎没有遗漏任何东西。我使用相同的代码进行另一个查询,除了sql不同。但我认为我的SQL很简单。这是在一个实例中生成的sql(我已经双重检查,所有表和列名都正确):

SELECT OrderDate, MenuItem From MenuItems, Orders WHERE Orders.itemID = MenuItem.ID AND Orders.orderDate BETWEEN '11/21/2012' AND '11/24/2012'

3 个答案:

答案 0 :(得分:1)

嗯,ExecuteNonQuery方法用于更改数据的语句,即。 DELETE / UPDATE / INSERT,返回值是该语句影响的行数。 由于您使用的是Select语句,因此您应该使用oledbDataAdapter和Fil DataSet来使用。

Dim conn As New OleDbConnection(con)
Dim adapter As New OleDbDataAdapter()
sql = "SELECT OrderDate, MenuItem FROM MenuItems, Orders WHERE Orders.itemID = MenuItem.ID AND Orders.orderDate BETWEEN '" + fromDate + "' AND '" + toDate + "'"
adapter.SelectCommand = new OleDbCommand(sql, con)
adapter.Fill(dataset)
Return dataset

答案 1 :(得分:1)

问题是拼写错误的表格。 (MenuItem而不是MenuItems),但它没有解决问题,我仍然有一个错误。事实证明,数据库与用作查询参数的datepicker值之间的匹配格式存在问题。

所以我确保以短日期格式保存到数据库:

sql = "INSERT INTO Orders(itemID, OrderDate) VALUES('" + ListBox1.SelectedValue.ToString() + "','" + FormatDateTime(OrderDate.Value, DateFormat.ShortDate) + "')"

答案 2 :(得分:1)

您应该使用参数化查询至少有两个原因。

  1. 您不必担心日期(和其他)文字和语言环境问题。

  2. 您不必担心SQL注入攻击,有人在文本框中输入恶意代码,将SQL语句转换为有害的语句。

  3. 将您的陈述更改为

    sql = "SELECT Orders.OrderDate, MenuItems.MenuItem " & _
        "FROM MenuItems INNER JOIN Orders ON MenuItems.ID = Orders.itemID " & _
        "WHERE Orders.orderDate BETWEEN ? AND ?"
    

    然后执行这样的命令

    Dim fromDate, toDate As DateTime
    
    fromDate = DateTime.Parse(fromDateTextBox.Text)
    toDate = DateTime.Parse(toDateTextBox.Text)
    
    Dim dataset As New DataSet()
    Using conn As New OleDbConnection(connectionString)
        Using adapter As New OleDbDataAdapter()
            Dim cmd As New OleDbCommand(sql, conn)
            cmd.Parameters.Add("?", fromDate)
            cmd.Parameters.Add("?", toDate)
            adapter.SelectCommand =  cmd
            adapter.Fill(dataset)
        End Using
    End Using