【问题标题】:When is "Try" supposed to be used in C# method names?什么时候应该在 C# 方法名称中使用“Try”?
【发布时间】:2013-06-16 23:02:19
【问题描述】:

我们正在与我们的同事讨论如果方法名称以“Try”开头意味着什么。

有以下意见:

  • 当方法可以返回空值时使用“Try”。
  • 当方法不会抛出异常时使用“Try”。

官方定义是什么?方法名称中的“Try”是什么意思? 对此有官方指南吗?

【问题讨论】:

  • +1 对函数名称进行了如此深思熟虑的人实际上是在寻找“下一个人”。不知道为什么这会获得接近的选票(这是来自一个今晚投了 很多 票的人。)
  • @JonathonReinhart,因为 “就目前而言,这个问题不适合我们的问答格式。我们希望答案得到事实、参考或具体的支持专业知识,但这个问题可能会引起辩论、争论、投票或扩展讨论。”
  • 微软有一份官方声明回答了这个问题(见我的回答)。这怎么不是事实?
  • @PranavHosangadi 正如 Erik 提到的,它有事实支持。此外,这里有很多非常有经验的 C# 开发人员,他们具有特定专业知识来提供有效的答案。见鬼,Eric Lippert 是首席 C# 语言架构师。我认为您可以称其为特定专业知识
  • @ErikSchierboom 这是 MS 指南是事实。 MS 指南是正确的使用指南是主观的和值得商榷的。

标签: c# naming-conventions


【解决方案1】:

(已更正) 正如 Erik 建议的那样,有官方指南。

当我看到TrySomething 方法时,我认为它

  • 不扔
  • 返回bool
  • 如果我期望值,它通过'out'参数返回
  • 存在Something 方法,它允许我自己处理任何异常。 (编辑,由 Jesse Webb 建议)

【讨论】:

  • 更正 - 它有官方指南。请参阅 Erik 的回答。
  • +1 但我也有第四个期望:如果有一个TryFoo 方法,就会有一个类似的Foo 方法,它允许我自己处理任何` 异常。这些方法的签名可能会有所不同,因此如果不更改其他代码,它们的用法就不能互换。
  • @JesseWebb,感谢您指出这一点。如果您不介意,我已将您的评论添加到我的回答中。
  • “不扔”在我看来过于笼统了。例如,如果 Int32.TryParse(String, NumberStyles, IFormatProvider, Int32) 不喜欢 style 参数,则抛出 ArgumentException。
  • 我同意“不抛出”可能被认为过于笼统,但我相信其意图是传达它不会作为执行的结果而不是作为值的结果参数。
【解决方案2】:

你必须在方法名中使用“Try”,当你想表明方法调用会产生无效结果的事实时。顺便说一下,按照 .NET 标准,它不是引发异常的函数,而是返回一些 VALIDNON_VALID 的函数,从程序的角度来看,值。

最后,这一切都与您决定在小组中使用的命名约定有关。

【讨论】:

    【解决方案3】:

    这被称为 TryParse 模式,已被 Microsoft 记录。 official Exceptions and Performance MSDN page says

    对于可能在常见情况下抛出异常的成员考虑 TryParse 模式,以避免与异常相关的性能问题。

    因此,如果您的代码在常规用例中意味着它可能会引发异常(例如解析 int),则 TryParse 模式是有意义的。

    【讨论】:

    • 另一个记录此模式的有用链接(搜索 TryParse)blogs.msdn.com/b/kcwalina/archive/2005/03/16/396787.aspx
    • 基本上,如果你有一个 TryParse 方法,你应该有一个 Parse 方法,当 TryParse 返回 false 时抛出。相反,如果你有 Parse 方法,你应该考虑有一个 TryParse 方法,当 Parse 抛出时返回 false
    • +1。除此之外,例外通常是针对“特殊”情况的。如果你正在做的事情很容易失败并且失败并不特别明显,那么使用这种模式比 try/catch 更习惯
    • 基本的东西,但这并不意味着指南没有用。如果您对平台不够了解,则很难正确掌握基本知识。
    • @daveL:这是基本的,是的,但是不同的约定(ParseOrNullParse)甚至相反的约定(ParseParseOrThrow)也一样基本。 Microsoft 指南的好处在于它促进了一致性:当您查看不熟悉的代码库时,您仍然可以理解它,因为它(很可能)使用了平台所有者认可的广泛约定。
    【解决方案4】:

    我认为当你想继续时应该使用try。方法是否返回一些值并不重要。

    案例1:如果返回正常,您可以通过某种方式继续。

    情况2:如果不返回:还是可以的;您可以通过其他方式继续。

    如果您希望某个值作为该方法的输出,请使用 out 参数。

    示例

    int value
    if (dictionary.TryGetValue("key", out value))
    {
        // Proceed in some way
    }
    else
    {
        // Proceed in some other way
    }
    

    【讨论】:

      【解决方案5】:

      如果出现以下情况,请确保在方法名称中包含 try

      • 你不会抛出任何异常
      • 您的方法具有以下签名:bool TrySomething(input, out yourReturn)

      所以基本上,如果我们使用try-methods,我们只会得到一个布尔结果。

      所以下面的代码不会抛出任何异常:

      string input = "blabla";
      int number;
      if (int.TryParse(input, out number))
      {
      // wooohooo we got an int!
      } else
      {
      //dooh!
      }
      

      而这段代码可以(并且在这种情况下会)抛出异常:

      string input = "blabla";
      int number;
      try
      {
           number = int.Parse(input); //throws an exception
      }
      catch (Exception)
      {
           //dooh!
      }
      

      使用 Try 方法是一种更安全、更具防御性的编码方式。 此外,如果代码 sn-p #2 不是整数,则执行起来需要更高的性能。

      【讨论】:

      • 如果您希望它在此上下文中更有意义,您的代码 sn-p #2 应为 int number = int.Parse(input);
      • @PierreArnaud 谢谢,改了!
      • 您仍然缺少 try 块之前的 int number; 声明和 number = ... 赋值。
      • @PierreArnaud 谢谢,我现在也包含了“int number”。
      • 请注意,如果异常与正在执行的直接操作(如TryLoadFile(path, out file) woah,内存不足)有些无关,您仍可能抛出异常。因此,调用者会期望路径错误或访问被拒绝不会出现错误,但也会出现可能出错的更奇怪的事情的异常。并记录下来。
      【解决方案6】:

      鲍勃叔叔在他的清洁代码一书中给出了下面的例子。每当我们期望抛出异常时,我们可以在方法名称中使用 Try 前缀:

      public void sendShutDown()
      {
          try{
              tryToShutDown();
          } catch (DeviceShutDownError e) {
              logger.log(e);            
          }
      }
      

      然后(改编):

      private void tryToShutDown()
      {
          //some code with no error handling, but
          //something might go wrong here
      }
      

      tryToShutDown 方法不进行任何错误处理,因为这是 sendShutDown 方法的职责。

      Microsoft 的TryParse 模式违反了干净的代码准则,即我们应该避免输出参数。

      如果我们不开发新版本的 C#,我们不必遵守所有 Microsoft 准则。有时它们不是最好的。

      【讨论】:

      • 这个答案为 Microsoft 的 Try-Parse 模式不适合案例时的处理提供了很好的建议。 .NET 中名为 Try...() 的方法暗示 Try-Parse 实在是太糟糕了,因为在很多情况下,除了解析之外还需要尝试其他的东西。
      猜你喜欢
      • 1970-01-01
      • 2011-11-01
      • 2010-12-30
      • 2012-03-23
      • 2010-10-18
      • 2018-06-20
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多