c#:try / catch如何清除导致错误的文本框?

时间:2010-11-10 09:04:36

标签: c# exception-handling

我想知道是否有一种方法可以使catch语句清除导致错误的文本框。到目前为止,这是我的验证码:

private bool ValidateForm()
{
    int val1, direction = 0;
    double speed = 0.0;

    bool validated = false;

    if (txtName.Text != "")
    {
        try
        {
            // attempts to convert values into their primary data types.
            // Any errors will throw an exception that will be reported
            // as invalid data

            val1 = Convert.ToInt32(txtXPos.Text);
            val1 = Convert.ToInt32(txtYPos.Text);
            speed = Convert.ToDouble(txtSpeed.Text);
            direction = Convert.ToInt32(txtDirection.Text);

            validated = true;
        }
        catch
        {
            MessageBox.Show(
              "You have an invalid value entered. Please check your entry.",
              "Invalid Values", MessageBoxButtons.OK, MessageBoxIcon.Error);
        }

        if (speed < 0.0 || speed > (double)newAirplane.PlanePosition.MaxSpeed)
        {
            MessageBox.Show(
              "Speed entered is out of range.",
              "Invalid Values", MessageBoxButtons.OK, MessageBoxIcon.Error);
        }

        if (direction < 0 || direction > 359) 
        {
            MessageBox.Show(
              "Direction is out of range",
              "Invalid values", MessageBoxButtons.OK, MessageBoxIcon.Error);
        }
    }
    else
    {
        MessageBox.Show(
            "Please enter a name.",
            "Blank Name", MessageBoxButtons.OK, MessageBoxIcon.Error);
    }

    return validated;
}

7 个答案:

答案 0 :(得分:2)

您可以在try块之外声明一个变量:

TextBox lastTextBox = null;

然后在每次转换之前,将其设置为您将从中获取值的文本框,如下所示:

lastTextBox = txtXPos;
val1 = Convert.ToInt32(txtXPos.Text);

然后在你的catch区块中:

if (lastTextBox != null)
    lastTextBox.Text = "";

答案 1 :(得分:2)

假设这是Winforms,最好的办法是使用内置的ErrorProvider,而不是尝试使用自己的验证框架。

答案 2 :(得分:1)

我建议您使用Int32.TryParse Method和Double.TryParse

而不是“Try Catch”块

答案 3 :(得分:1)

这里需要注意的重点是,您在非特殊情况下使用例外情况。也就是说,输入无效数字的用户并不例外 - 这几乎是预期的!

您应该使用TryParse方法:

bool xValValid = Int32.TryParse(txtXPos.Text, out val1);
if(!xValValid){
  txtXPos.Text = "";
  validated = false;
  MessageBox.Show("You have an invalid value entered. Please check your entry.", "Invalid Values", MessageBoxButtons.OK, MessageBoxIcon.Error);

}

答案 4 :(得分:1)

您还可以将单个文本框的逻辑提取为:

private bool Validated<T>(Control tb, out T value)
{
    try
    {
        value = return (T)Convert.ChangeType(tb.Text, typeof(T));
        return true;
    }
    catch
    {
        value = default(T);
        tb.Text = "";
        return false;
    }
 }

你可以简单地用作:

if (!Validated<int>(txtXPos, out val1) ||
    !Validated<int>(txtYPos, out val2) ||
    !Validated<double>(txtSpeed, out speed) ||
    !Validated<int>(txtDirection, out direction))
{
     MessageBox.Show("Validation failed");
}

<强> [编辑]

此外,从可用性的角度来看,清除文本框是一个坏主意,尤其是在TextChanged事件中。如果我不小心在里面输入一个字母,我不希望我的文本框被清除。更好的方法是使用ErrorProvider,或以其他方式不引人注意地指出输入是错误的。

<强> [EDIT2]

使用Convert.ChangeType可以从字符串转换为基本类型,但是如果需要将更复杂的字符串解析为自己的类,则可以提供任何您喜欢的转换方法:

private bool Validated<T>(Control tb, Func<string, T> converter, out T value)
{
    try
    {
        value = converter(tb.Text);
        return true;
    }
    catch
    {
        value = default(T);
        tb.Text = "";
        return false;
    }
 }

然后像这样使用它:

if (!Validated<int>(txtXPos, Convert.ToInt32, out val1) ||
    !Validated<int>(txtYPos, Convert.ToInt32, out val2) ||
    !Validated<double>(txtSpeed, Convert.ToDouble, out speed) ||
    !Validated<int>(txtDirection, Convert.ToInt32, out direction))
{
        MessageBox.Show("Validation failed");
}

通过这种方式,您可以传递任何具有签名Func<string, T>的委托,该签名将执行实际转换,或者如果失败则抛出异常。

答案 5 :(得分:0)

我建议制作一个像

这样的功能
private bool TryReadClear(TextBox txtBox, out double value)
{
  if (double.TryParse(txtBox.Text, out value))
  {
    txtBox.BackColor = Color.White;
    return true;
  }
  else
  {
    txtBox.BackColor = Color.Red;
    txtBox.Text = string.Empty;
    return false;
  }
}

然后用这个简化的代码替换你的try / catch块:

    validated = validated && TryReadClear(txtXPos, out val1);
    validated = validated && TryReadClear(txtYPos, out val1);
    validated = validated && TryReadClear(txtSpeed, out speed);
    validated = validated && TryReadClear(txtDirection, out direction);
    if (!validated)
    {
      MessageBox.Show("You have an invalid value entered. Please check your entry.", "Invalid Values", MessageBoxButtons.OK, MessageBoxIcon.Error);
    }

此方法的好处是,它会检查每次通过的所有文本框,并清除所有无效文本框。使用@ cdhowie的解决方案只会清除第一次失败,而不是全部。

编辑:您甚至可以做一些很酷的事情,比如将背景颜色设置为红色以直观地突出显示不良文本框(编辑上面的代码以显示示例)。

答案 6 :(得分:0)

    private bool ValidateForm()
            {
                int val1, direction = 0;
                double speed = 0.0;

                bool validated;
                if (txtName.Text != "")
                {
                    try
                    {
                        //attempts to convert values into their primary data types. Any errors will throw an exception that will be reported as invalid data
                        int counter = 1;
                        val1 = Convert.ToInt32(txtXPos.Text);
                        counter = counter + 1;
                        val1 = Convert.ToInt32(txtYPos.Text);
                        counter = counter + 1;
                        speed = Convert.ToDouble(txtSpeed.Text);
                        counter = counter + 1;
                        direction = Convert.ToInt32(txtDirection.Text);
                        validated = true;
                    }
                    catch
                    {
                    switch(counter)

                      case 1:

                     txtXPos.Text="";
                      break;
                      case 2:

                      txtYPos.Text="";
                        break;
                      case 3:

                     txtSpeed.Text="";
                     break;
                     case 4:

                     txtDirection.Text="";
                      break;
                     default:
                     break;
                        MessageBox.Show("You have an invalid value entered. Please check your entry.", "Invalid Values", MessageBoxButtons.OK, MessageBoxIcon.Error);
                        validated = false;
                    }
                    if (speed < 0.0 || speed > (double)newAirplane.PlanePosition.MaxSpeed)
                    {
                        MessageBox.Show("Speed entered is out of range.", "Invalid Values", MessageBoxButtons.OK, MessageBoxIcon.Error);
                        validated = false;
                    }
                    if (direction < 0 || direction > 359)
                        MessageBox.Show("Direction is out of range", "Invalid values", MessageBoxButtons.OK, MessageBoxIcon.Error);
                }
                else
                {
                    MessageBox.Show("Please enter a name.", "Blank Name", MessageBoxButtons.OK, MessageBoxIcon.Error);
                    validated = false;
                }



                return validated;

            }

认为这是你所期待的。