【问题标题】:C#: Code Contracts vs. normal parameter validationC#:代码契约与普通参数验证
【发布时间】:2009-12-30 15:18:41
【问题描述】:

考虑以下两段代码:

    public static Time Parse(string value)
    {
        string regXExpres = 
           "^([0-9]|[0-1][0-9]|2[0-3]):([0-9]|[0-5][0-9])$|^24:(0|00)$";
        Contract.Requires(value != null);
        Contract.Requires(new Regex(regXExpres).IsMatch(value));
        string[] tokens = value.Split(':');
        int hour = Convert.ToInt32(tokens[0], CultureInfo.InvariantCulture);
        int minute = Convert.ToInt32(tokens[1], CultureInfo.InvariantCulture);
        return new Time(hour, minute);
    }

    public static Time Parse(string value)
    {
        if (value == null)
        {
            throw new ArgumentNullException("value");
        }
        string[] tokens = value.Split(':');
        if (tokens.Length != 2)
        {
            throw new FormatException("value must be h:m");
        }
        int hour = Convert.ToInt32(tokens[0], CultureInfo.InvariantCulture);
        if (!(0 <= hour && hour <= 24))
        {
            throw new FormatException("hour must be between 0 and 24");
        }
        int minute = Convert.ToInt32(tokens[1], CultureInfo.InvariantCulture);
        if (!(0 <= minute && minute <= 59))
        {
            throw new FormatException("minute must be between 0 and 59");
        }
        return new Time(hour, minute);
    }

我个人更喜欢第一个版本,因为代码更清晰更小,并且可以轻松关闭合约。但缺点是 Visual Studio Code Analysis 指责我应该检查参数值是否为 null 并且构造函数的 Contracts 没有意识到正则表达式确保分钟和小时在给定的边界内。

所以我最终得到了很多错误的警告,而且我看不出有任何方法可以使用合同验证字符串值,而不会最终抛出除 RegEx 验证之外的 FormatExceptions。

您有什么建议可以使用代码合同解决这种情况和类似情况吗?

【问题讨论】:

  • 您确实意识到您可以重写第二个示例以使用相同的正则表达式,对吧?这将使这两个示例更加相似。

标签: c# .net .net-4.0 code-contracts microsoft-contracts


【解决方案1】:

为了摆脱警告,您可以使用Contract.Assume

【讨论】:

  • 这种解决了我的问题。如果我在 return 语句前面添加以下行,所有错误的警告都消失了。唯一我仍然不喜欢的是这些行以某种方式破坏了代码。但是我想代码契约不可能得到正则表达式的含义。 Contract.Assume(0
  • @steveee,您应该始终在连词上拆分合同,以便 Contract.Assume(0 &lt;= hour &amp;&amp; hour &lt;= 24); 变为 Contract.Assume(0 &lt;= hour); Contract.Assume(hour &lt;=24);
  • @Porges 有文件解释原因吗?
  • @ssg:我不认为它在文档中,但是如果您搜索代码合同 MSDN 论坛,则会有来自开发人员的信息,例如:“将连词拆分为不同的合同使静态检查器更加精确,并且您会收到更好的错误消息。”
猜你喜欢
  • 1970-01-01
  • 2013-03-06
  • 2013-10-27
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多