c#

时间:2016-03-09 12:30:03

标签: c# mysql string format

我在ASP.NET c#和MySQL数据库中工作。

我一直收到错误:

  

索引(从零开始)必须大于或等于零且小于   参数列表的大小。

我的代码:

string sql = String.Format(@" UPDATE `doTable` ");
sql += String.Format(" SET Active = {0} ");
sql += String.Format(" WHERE ID = {1}; ", Active.ToString(), ID.ToString());

如果尝试这个而不是代码工作,有什么区别? :

string sql = String.Format(@"UPDATE `doTable` SET 
                                     Active = {0}
                                     WHERE ID = {1}; ",
                                     Active.ToString(),
                                     ID.ToString());

你能帮我解决一下这个问题吗?

5 个答案:

答案 0 :(得分:3)

该行的问题;

sql += String.Format(" SET Active = {0} ");

您为String.Format声明了一个索引组件,但您从未添加它的格式字符串组件。但在你的第二个例子中,你做到了。每个陈述都是独立的。这就是为什么这行抛出异常而你的第二个代码部分没有。

来自Composite Formatting文档;

  

一个   如果是参数说明符,则在运行时抛出FormatException   指定对象列表范围之外的项目。

但不要这样使用!

您应始终使用parameterized queries。这种字符串连接对SQL Injection攻击开放。

using(var con = new MySqlConnection(conString))
using(var cmd = con.CreateCommand())
{
     cmd.CommandText = "UPDATE `doTable` SET  Active = @active WHERE ID = @id";
     cmd.Parameters.Add("@active", MySqlDbType.VarChar).Value = Active.ToString();
     cmd.Parameters.Add("@id", MySqlDbType.VarChar).Value = ID.ToString();
     // I assumed your columns are VarChar type.

     con.Open();
     cmd.ExecuteNonQuery();
}

强烈怀疑你的ID应该是数字类型而不是基于它的名字的字符。

答案 1 :(得分:1)

如果你真的想以这种方式构建你的查询,你应该修改你的代码:

string sql = String.Format(@" UPDATE `doTable` ");
sql += String.Format(" SET Active = {0} ", Active.ToString());
sql += String.Format(" WHERE ID = {0}; ",  ID.ToString());

但这是不好的方法。考虑使用 SqlCommand参数https://msdn.microsoft.com/en-us/library/system.data.sqlclient.sqlcommand(v=vs.110).aspx

答案 2 :(得分:0)

您在两个不同的字符串中定义了2个参数。 将其更改为:

string sql = String.Format(@" UPDATE `doTable` ");
sql += String.Format(" SET Active = {0} ", Active.ToString());
sql += String.Format(" WHERE ID = {0}; ", ID.ToString());

答案 3 :(得分:0)

您应始终提供与最大占位符值+ 1一样多的参数。

代码中的第二行包含占位符{0},但不提供值作为参数,因此软件无法完成字符串。

在第二个示例中,您提供了两个占位符{0}{1}以及两个参数(Active.ToString()ID.ToString()),因此两个占位符都可以替换为参数。

您还可以提供比占位符更多的参数(例如代码的第三行),但这很少有意义,因为不会使用额外的值。

答案 4 :(得分:0)

不要使用String.Format来构建查询。这对sql注入是开放的,你应该使用SqlCommand.Parameters。此外,对于带有DataTime类型的ToString()和依赖于文化的十进制,你可能会遇到很多问题。

string sql = @"UPDATE [doTable] 
                  SET Active = @Active
                WHERE ID = @ID";

using (SqlCommand cmd = new SqlCommand(sql)) {
  cmd.Parameters.AddWithValue("@ID", ID);
  cmd.Parameters.AddWithValue("@Active", Active);