2011-04-08 225 views
0

该程序是假定计算数据库中的翻新并在文本框中返回一个值。我初始化我的值为0,但我的问题是我怎么得到它来计算每次用户扫描一个单位被重新打磨。我试图做的任何事情都会在我的程序中给我一个错误。现在它的返回值为1,因为我添加了RefurbRate ++。谁能帮我?如何获得一个值在文本框中返回?

以下是我和我的代码完成:

收起

private int GetRefurbRate() 
{ 
    string sql = ""; 
    int Refurb_Rate = 0; 
    int totalRefurb = 0; 
    int totalUnits = 0; 
    string error_msg = ""; 

    sql = "SELECT COUNT(*) " + 
      "FROM " + schema + ".repair_part rp " + 
      "WHERE rp.repair_ord = '" + txtRO.Text + "' "; 
    while (true) 
    { 
      if (!myDb.RunSql(sql, true)) 
      { 
      error_msg = "DBError for getting Refurb Rate"; 
      break; 
      } 
      if (myDb.dbRdr.HasRows) 
      { 
       if (myDb.dbRdr.Read()) 
       { 
       try 
       { 
        Refurb_Rate = (totalRefurb/totalUnits * 100); 
       } 
       catch (Exception e) 
       { 
         Console.WriteLine(e); 
       } 
       } 

       Refurb_Rate++; 
      } 
      break; 
    } 
    myDb.dbRdr.Close(); 
    if (error_msg != String.Empty) 
    { 
     MessageBox.Show(error_msg, "Get Refurb Rate", 
          MessageBoxButtons.OK, MessageBoxIcon.Asterisk); 
    } 
    return Refurb_Rate; 
} 
+0

Ummmmm你可以问以另一种方式的问题,因为它不作出任何意义,我。 – 2011-04-08 21:58:49

+0

您的代码中没有文本框,我们如何提供帮助? – 2011-04-08 22:03:53

+1

他**是什么“翻新”? “扫描单元重新扫描”意味着什么? – 2011-04-08 22:04:08

回答

0

有你需要解决,才能解决这个poroblem几个问题。

首先和最重要的是是你的应用程序容易受到SQL注入。这会让不好的人对你的数据库做坏事。请阅读parameterized queries以防止出现这种情况。

其次,我不知道myDb.RunSql(sql, true)是做什么的,但似乎没有使用标准方法从数据库使用C#查询数据。通常要使用以下方法:如果您使用这些会更容易让我们来告诉你你在做什么错

  • 的SQLConnection
  • 的SqlCommand
  • SqlDataReader的

。如果你推出自己的东西会更困难。

如果您查看MSDN的SQLDataReader代码示例,它将向您展示如何使用这三个类连接到数据库,执行命令并处理结果。与totalUnits

http://msdn.microsoft.com/en-us/library/system.data.sqlclient.sqldatareader.aspx

2

这个错误来自除以零错误:请点这里。它始终为零。当错误被抛出时,它被catch块所吃掉,它不会向调用者报告错误。这使得该方法来完成,并且将始终返回1

+0

我明白了,但我该如何让公式具有除0之外的值?我不知道该怎么做。 – Justin 2011-04-08 22:36:06

+0

@Justin你不能使用你正在使用的类型。 JIM编译器的建议似乎是合理的,并解释了这个问题。您可以使Refurb_Rate成为double并在返回之前将其转换为int。或者我想你可以将你的赋值改为Refurb_Rate:'Refurb_Rate = totalRefurb * 100/totalUnits;'注意在除以totalUnits之前将totalRefurb乘以100可以避免Snowbear JIM编译器描述的问题。 – 2011-04-08 22:59:26

0

胡乱猜测,你有结果总是等于零,因为你将int号位置:

totalRefurb/totalUnits * 100 

所以如果totalRefurb小于totalUnits和大于零,那么结果将始终为零,因为它们以“整数”方式分割。你应该投其中一人双:

double refurb_Rate = ((double)totalRefurb/totalUnits * 100); 

当然,我们还应该提到的是,编写代码的方式,这使得许多其他错误,很有可能的。

+0

我不断收到你无法将double转换为int错误的错误。我假设另一个程序员使变量成为一个整数,并影响到我。有什么办法可以使得整数除0之外还有一个值? – Justin 2011-04-08 22:37:32

0
  1. 您正在使用字段(myDb)来保存自定义数据库接口对象。这很糟糕,因为它构成不好。使用相同对象的多种方法可能会相互干扰。由于必须考虑整个计划,因此很难推断它的使用方式。尽可能避免这种持久状态。更好的方法是将有状态对象传递给需要它的方法,而无需在字段中引用它。更好的办法是完全放弃接口,并使用.NET框架提供的数据库对象。

    1. 您正在动态创建SQL语句作为字符串。这很糟糕,因为它会让你打开SQL注入攻击(特别是当文本框的内容被粘贴到字符串中时!“; DELETE FROM repair_ord; - ”)。一个更好的方法是使用存储过程,或者至少改变,以便在您的语句中使用命名参数。显然,这是为了改变模式(改变环境?)。在整个数据库之间切换会更安全。

    2. 你有一个恒定的真正控制的表达,这也是没有用处的,因为控制的每一个流程内循环导致break语句在while循环数据库读取的代码。如果这是为了在第一个if语句结束时创建一个隐含的goto,那么有更好的方法来做到这一点(就像其他的一样)。 while语句和break语句应该被删除。

    3. 您似乎没有使用从任何地方的select语句返回的值。

    4. 变量totalRefurb和totalUnits不会被置为零以外任何东西。因此,该部门将始终抛出一个DivisionByZeroException。因此,Refurb_Rate从零修改的唯一时间是在末尾增加。所以它总是以1的值结束。

    5. try/catch是完全不必要的。显然,它放置在那里来处理DivisionByZeroException,但最好在分割之前通过检查totalUnits = 0来避免异常。

    6. catch语句不应该捕获一般的Exception对象。相反,如果无法避免,并且您知道如何处理它,则应该捕获并处理您期望的特定异常。

    7. 文体上,它最好限制在其中变量用于尽可能小程序文本的量。因此,最好在初始化它的同一行上声明sql变量。也没有理由将它初始化两次,就像你在开始时将它设置为等于空字符串一样。

这里是你的程序的另一个版本:

private static int GetRefurbRate(string repairOrd, int totalUnits, string connection, string schema) 
{ 
    if (string.IsNullOrEmpty(repairOrd)) 
     return 0; 
    if (totalUnits == 0) 
     return 0; 
    if (string.IsNullOrEmpty(connection)) 
     throw new ArgumentException("Missing database connection for getting the refurb rate."); 
    if (string.IsNullOrEmpty(schema)) 
     throw new ArgumentException("Missing schema for getting the refurb rate."); 

    string sql = string.Format(@" 
      SELECT COUNT(*) AS TotalRefurb 
      FROM {0}.repair_part rp 
      WHERE rp.repair_ord = @repair_ord 
     ", schema); 

    int totalRefurb; 
    using (SqlConnection conn = new SqlConnection(connection)) 
    { 
     conn.Open(); 
     using (SqlCommand comm = new SqlCommand(sql, conn)) 
     { 
      comm.CommandType = CommandType.Text; 
      comm.Parameters.AddWithValue("@repair_ord", repairOrd); 
      using (SqlDataReader reader = comm.ExecuteReader()) 
      { 
       reader.Read(); 
       totalRefurb = (int)reader["TotalRefurb"]; 
      } 
     } 
    } 
    return totalRefurb/totalUnits * 100; 
} 
相关问题