【问题标题】:TryParse and VariablesTryParse 和变量
【发布时间】:2013-11-15 23:30:13
【问题描述】:

我刚刚学习 C#,我正在尝试更多地了解 TryParse 以及它如何与已建立的变量相关和交互。在下面的示例中,我只是确认文本框中的值是否确实是小数,并且它们是否在给定范围内。否则,我调用显示错误消息的 BadInput() 方法。

private void VerifyNums()
    {
        if (decimal.TryParse(Val1Box.Text, out Val1)&& (val1<=100) && (Val1>=0))
        {
            if (decimal.TryParse(Val2Box.Text, out Val2) && (Val2 <=100) && (Val2 >=0))
            {
                if (decimal.TryParse(Val3.Text, out Val3) && (Val3 <100) && (Val3 >=0))
                {
                    GoodInput();
                }
                else
                {
                    BadInput();
                }
            }
            else
            {
                BadInput();
            }
        }
        else
        {
            BadInput();
        }
    }

第一个问题:OUT 在 TryParse 中做了什么?它是否设置 Val1 等于文本框的内容?

第二个问题:是否可以解析和检查变量 Val1、Val2 和 Val3,然后能够将它们用作其他方法的输入或参数?如果是这样,那是怎么做的?我已经阅读了很多关于 OUT 和 REF 的内容,但我只是不明白它们是如何工作的。

【问题讨论】:

    标签: c#


    【解决方案1】:

    OUT 在 TryParse 中做了什么?是否设置 Val1 等于文本框的内容?

    它将Val 设置为decimal,由传递给第一个参数的字符串表示(在您的情况下,为TextBox 值)。

    out 表示该函数的 输出 将存储在该变量中。它是 return 值的替代品,例如 int.Parse 使用:

    decimal val = decimal.Parse("123");
    

    由于函数只能返回一个值,MS 选择返回bool 并使用out 参数作为解析结果,而不是返回复合结构或使用bool 作为out 参数:

    bool isSussessful;
    decimal val = int.TryParse("123", out isSuccessful);
    

    但这会阻止将解析内联到 if 语句中。

    您的错误是由于没有声明 Val1 first:

        decimal Val1;
        if (decimal.TryParse(Val1Box.Text, out Val1)&& (Val1<=100) && (Val1>=0))
        {
            decimal Val2;
            if (decimal.TryParse(Val2Box.Text, out Val2) && (Val2 <=100) && (Val2 >=0))
            {
    

    是否可以解析和检查变量Val1Val2Val3,然后能够将它们用作其他方法中的输入或参数

    绝对 - 就像您对任何其他变量一样。 out 仅在将变量传递给函数时有所不同(ref 必须初始化变量,out 则不需要)。

    【讨论】:

    • 比如说,我在班级顶部有三个全局十进制变量:Val1 = 0、Val2 = 0、Val3 = 0。我如何解析和检查我的变量VarifyNums() 方法,然后更新我的全局变量以反映这些值?
    • 不确定“全局变量”是什么意思(因为 C# 中不存在这些变量)。如果您的意思是类的 fields,那么您的初始代码应该可以正常工作。否则你可以像我一样声明局部变量。
    • 我想这就是我的假设是错误的。那么如何将变量从一个私有方法传递到另一个私有方法呢?所以我在 VerifyNum() 中解析我的值,我想在另一个私有方法 DoMath() 中使用它们。
    • 我不确定我是否遵循 - 在您想要做什么的问题中添加一个 simple(如 1 个变量)示例。
    • 所以我在 VerifyNums 中解析和检查并设置我的值,现在我创建了另一个基本的私有方法 DoMath(),它只是添加了 Val1 + Val2 + Val3 并返回结果。如何确保值在 DoMath() 中可见且可用?我希望这能解决问题。
    【解决方案2】:

    作为参数方法前缀的out keyword 意味着被调用的方法应该以某种方式初始化变量(例如,文本框中的无效值导致 valX 参数初始化为零)。该变量当然在 TryParse 之后的调用方法中可用,因此可以用作其他方法或函数的参数

    bool v1Good = decimal.TryParse(Val1Box.Text, out Val1);
    bool v2Good = decimal.TryParse(Val2Box.Text, out Val2);
    bool v3Good = decimal.TryParse(Val3.Text, out Val3);
    
    if(v1Good && v2Good && v3Good)
    {
       if(val1 >=0 && val1 <= 100 && val2 >= 0 && val2 <=100 && val3 >= 0 && val3 <= 100)
       {
           // You could pass them to the GoodInput method
           GoodInput(val1, val2, val3);
       }
       else
           BadInput();
    }
    else
        BadInput();
    

    【讨论】:

      【解决方案3】:

      C# 中的out 关键字[MSDN] 表示方法(例如TryParse)必须在方法返回之前为该变量赋值。这为您提供了一个构造,该构造有效地为您提供来自单个方法的两个或多个返回值。 (谨慎使用。)

      您在 C# 中经常看到这种模式,无论是在框架代码还是用户代码中,如果操作失败,则需要抛出异常。例如,如果您将“Gonzo”传递给decimal.Parse 方法,则它没有可以有意义地返回给您的值来表明操作失败,因此它必须抛出异常。通过实现TryParse 模式,您可以返回一个布尔值,指示解析操作是否成功,如果成功,out 参数将具有该操作的结果。在操作失败的情况下,out 参数仍将被分配一个值,但您不能依赖该值来获得任何有意义的值。

      所以,回答您的问题 1: 是的,decimal.TryParseout 参数的值设置为来自文本框中的已解析文本,但前提是该文本是有效的小数,在这种情况下,该方法也返回true。如果文本不代表有效的小数,则该方法返回 false 并将 out 参数的值设置为零。

      至于问题2:当然可以在TryParse 完成后使用out 变量。像这样:

      decimal Val1;
      if (decimal.TryParse(Val1Box.Text, out Val1) && (Val1 <= 100) && (Val1 >= 0)
      {
          // Continue to use the variable Var1 as a valid decimal, 
          // because that's what it's guaranteed to be. 
          //
          // You're even able to use it within the conditional expression 
          // of the if statement as above.
      }
      

      【讨论】:

        【解决方案4】:

        1) C# 默认按值传递参数。 Out 允许通过引用而不是按值传递参数。实际上,这意味着您传递给函数的值可以在其中进行修改。

        回答你的问题:

        如果 TryParse 返回 true:则文本框的值被成功解析并分配给 Val1。 如果它返回 false:则转换失败,并且 Val1(或 Val2,或您尝试解析的任何内容)的值 will be zero

        2) Out 仅仅意味着它们的引用被传递给了一个函数(并且它们的值可能被修改了)。除此之外,您可以将它们视为普通变量(因为它们正是如此)。

        例如,做这样的事情是完全有效的:

        if (decimal.TryParse(Val1Box.Text, out Val1)&& (Val1<=100) && (Val1>=0))
        {
           GoodInput(Val1);
        }
        

        【讨论】:

          猜你喜欢
          • 2018-10-22
          • 1970-01-01
          • 1970-01-01
          • 2014-06-03
          • 2012-06-08
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          相关资源
          最近更新 更多