【问题标题】:Check user input for errors elegantly优雅地检查用户输入的错误
【发布时间】:2013-03-14 08:52:56
【问题描述】:

我的程序等待用户输入,并在适当的时候处理它。我需要检查用户输入以确保它满足某些标准,如果它不满足所有这些标准,它将被拒绝。

伪代码类似于:

if (fulfills_condition_1)
{
    if (fulfills_condition_2)
    {
        if (fulfills_condition_3)
        {
            /*process message*/
        }
        else
            cout << error_message_3; //where error_message_1 is a string detailing error
    }
    else
        cout << error_message_2; //where error_message_2 is a string detailing error
}
else
    cout << error_message_1; //where error_message_3 is a string detailing error

这些条件的数量有可能会增加,我想知道是否有一种更简洁的方式来使用 switch 或类似的东西来表示这一点,而不是大量的级联 if 语句。

我知道有可能使用

if (fulfills_condition_1 && fulfills_condition_2 && fulfills_condition_3)
    /*process message*/
else
    error_message; //"this message is not formatted properly"

但这没有第一个有用,并且没有说明问题出在哪里。

这些条件可以大致排列为越来越重要,即检查condition_1 比检查condition_3 更重要,所以if 语句确实有效 - 但一般来说有更好的方法吗?

【问题讨论】:

  • 您是否考虑过使用 try-catch 和异常类进行否定条件检查,以准确反映最初引发问题的条件?
  • 这取决于您输入的复杂程度。我会创建一个 DSL 来声明输入如何有效,并创建代表该 DSL 的对象,然后说验证这个输入。
  • @PeterWood 这是一些严格的错误检查!
  • @AlexChamberlain 好吧,有时重复的代码会变得无法维护。
  • 谢谢大家的帮助,这很有用!

标签: c++ if-statement error-handling


【解决方案1】:

怎么样

if (!fulfills_condition_1) throw BadInput(error_message_1);
if (!fulfills_condition_2) throw BadInput(error_message_2);
if (!fulfills_condition_3) throw BadInput(error_message_3);

/* process message */

然后您的异常处理程序可以报告错误消息,并根据需要重试或中止。

【讨论】:

    【解决方案2】:

    如果困扰您的是级联的ifs,您可以选择以下方法之一:

    使用布尔值:

    bool is_valid = true;
    string error = "";
    if (!condition_one) {
      error = "my error";
      is_valid = false;
    }
    
    if (is_valid && !condition_two) {
      ...
    }
    
    ...
    
    if (!is_valid) {
      cout << error;
    } else {
      // Do something with valid input
    }
    

    使用异常:

    try {
      if (!condition_one) {
        throw runtime_error("my error");
      }
    
      if (!condition_two) {
        ...
      }
    
      ...
    
    } catch (...) {
      // Handle your exception here
    }
    

    【讨论】:

      【解决方案3】:

      我建议你可以使用“提前返回”技术:

        if (!fulfills_condition_1)
           // error msg here.
           return;
      
        // fulfills_condition1 holds here.
      
        if (!fulfills_condition_2)
           // error msg here.
           return;
      
        // Both conditon1 and condition2 hold here.
      
        if (!fulfills_condition_3)
           // error msg here.
           return.
      

      【讨论】:

        【解决方案4】:

        如果要在几个地方重复使用,我会制作一个 DSL:

        Validator inputType1Validator =
            Validator.should(fulfill_condition_1, error_message_1)
                     .and(fulfill_condition_2, error_message_2)
                     .and(fulfill_condition_3, error_message_3)
        
        inputType1Validator.check(input);
        

        【讨论】:

          猜你喜欢
          • 2011-10-19
          • 2020-03-19
          • 2010-11-20
          • 2016-05-07
          • 1970-01-01
          • 1970-01-01
          • 2010-10-02
          • 1970-01-01
          • 1970-01-01
          相关资源
          最近更新 更多