【问题标题】:SqlCommand errorSqlCommand 错误
【发布时间】:2013-04-10 09:18:54
【问题描述】:

目前,我正在尝试使用我通过 C# 程序硬编码的 3 个值填充我的 SQL Server 数据库。

我的数据库有 4 列,如下所示:

  • RowID(这应该由我的数据库自动更新)
  • Name(存储为字符串)
  • Score (int)
  • Accuracy(浮点数)

在我的代码中,我尝试使用以下代码行来填写这些内容:

 using (SqlConnection connection = new SqlConnection(DBConnection))
 {
            string name = "John";
            int score = 123;
            float Accuracy = 20.0f;

            SqlCommand command = new SqlCommand("INSERT INTO HighScoreTable(Name, Score, Accuracy) VALUES("  + name + " , " + score + " , " + Accuracy + ")", connection);
            command.Connection.Open();
            command.ExecuteNonQuery();
        }

但是当我运行我的程序时,Visual Studio 会高亮显示

command.ExecuteNonQuery() 

声明“John”不是有效的列。

我做错了什么吗?

【问题讨论】:

  • 如果您花 10 秒时间在 StackOverflow 上搜索任何相关问题,您应该已经阅读过的一件事是:使用参数化查询,为了理智!!!
  • 这对你有用吗??

标签: c# database sql-server-2008


【解决方案1】:

(仅在我看来)正确的方法是:

using (SqlConnection connection = new SqlConnection(DBConnection))
{
    string name = "John";
    int score = 123;
    float Accuracy = 20.0f;

    using (SqlCommand command = new SqlCommand("INSERT INTO HighScoreTable(Name, Score, Accuracy) VALUES(@name, @score, @accuracy)", connection);
    {
        command.Parameters.AddWithValue("@name", name);
        command.Parameters.AddWithValue("@score", score);
        command.Parameters.AddWithValue("@accuracy", accuracy);

        command.Connection.Open();
        command.ExecuteNonQuery();
    }
}

请注意,您在使用参数化查询时不需要介意单引号!字符串参数没有用单引号括起来 - 都是由框架为您完成的。

【讨论】:

    【解决方案2】:

    这里有很多错误。

    1. 如果你想这样插入,你需要在周围添加“'” 你的价值观。
    2. 您需要在值之间使用逗号。
    3. SQL 注入的时机已经成熟
    4. 性能不佳,因为每个查询都不同。

    您实际上想要添加参数(AddParameterWithValue)

    看这里:

    SQL injection on INSERT

    【讨论】:

    • 1) 不太正确。如果值是字符串,则需要将值包含在单引号中。数字可以不用单引号。
    • 同意。这里的主要问题是不使用参数,所以没有实际意义。
    【解决方案3】:

    对此类问题使用参数化查询:

    using (SqlConnection connection = new SqlConnection(DBConnection))
            {
                string name = "John";
                int score = 123;
                float Accuracy = 20.0f;
    
                SqlCommand command = new SqlCommand("INSERT INTO HighScoreTable(Name, Score, Accuracy) VALUES(@name,@score,@accuracy)", connection);
    
                   SqlParameter name= new SqlParameter("@name", name);
                    name.Value = name;
                    command.Parameters.Add(name);
                   .
                   . 
                   .
                command.Connection.Open();
                command.ExecuteNonQuery();
            }
    

    这样可以添加参数,避免列混淆。

    【讨论】:

    • 你写它的方式是相当多余的。您可以使用AddWithValue。此外,您使用的SqlParameter 构造函数已经设置了参数的值,因此不需要name.Value = ... 行。
    • @ThorstenDittmar 是的,最近我开始编写参数化查询,在此之前我曾经写过与海报所写相同的查询。我看到了你的回答,这对我来说已经不再有教育意义了。谢谢。
    【解决方案4】:

    由于 John 是一个字符串,您必须通过在 John 的任一侧添加 ' 来让您的数据库知道这一点。

    所以把...VALUES(" + name + " , "...改成...VALUES('" + name + "' , "...

    如果您只写 John 没有 ' 在任何一边,那么数据库会认为您指的是一个列,并且正如您的错误消息所示:数据库对名为 John 的列一无所知。

    【讨论】:

    • @ThorstenDittmar - 我只是指出了他的代码有什么问题(从 SQL 服务器的角度来看)。我从不鼓励将连接的字符串发送到数据库,但我想我也可以在我的回答中指出它;)
    【解决方案5】:

    我怀疑你没有逃脱文本。

    SqlCommand command = new SqlCommand("INSERT INTO HighScoreTable(Name, Score, Accuracy) VALUES("'" + name + "' , " + score + " , " + Accuracy + ")"
    

    更好的方法是使用正确的命令参数:

    When should "SqlDbType" and "size" be used when adding SqlCommand Parameters?

    【讨论】:

      【解决方案6】:

      这样做才能正常工作

      SqlCommand command = new SqlCommand("INSERT INTO 
            HighScoreTable(Name, Score, Accuracy) 
                     VALUES('"  + name + "' , " + score + " , " + Accuracy + ")", connection);
      

      因为名称是字符串值,所以只需像这样'" + name + "'' 装饰它,因为在sql server 中,如果字符串不是用' 装饰,它会给你一个错误

      现在字符串值被转换为以下 sql 查询无效

            INSERT INTO 
            HighScoreTable(Name, Score, Accuracy) 
                     VALUES(John , 123 , 20.0f)
      

      为避免此错误,请使用 SQLParameter,即参数化查询

      【讨论】:

        【解决方案7】:

        首先,我强烈建议您采用不同的方法 - 尽快进行参数化查询。它将防止 SQL 注入并使您的生活更轻松,因为您不必每次都考虑格式化您的 SQL 查询。一段时间后,想知道所有引号应该放在哪里会变得非常乏味,而且很痛苦在维护期间修改此类代码...

        其次,您的 SQL 转换为如下所示:

        SqlCommand command = new SqlCommand("INSERT INTO HighScoreTable(Name, Score, Accuracy) VALUES(John , 10 , ..)", connection);
        

        SQL 认为您的值实际上是列名!您需要将值用单引号括起来

        INSERT INTO HighScoreTable(Name, Score, Accuracy) VALUES('John' , 10 , '..')
        

        【讨论】:

        • 但是ScoreINT - 所以你为 score 提供的值真的不应该用引号......
        猜你喜欢
        • 2013-10-14
        • 2017-07-06
        • 2021-08-29
        • 2015-12-06
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2011-01-06
        • 1970-01-01
        相关资源
        最近更新 更多