Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/csharp/285.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
C# 如果异常无法发生,是否应该抛出并处理它?_C#_Validation_Exception Handling - Fatal编程技术网

C# 如果异常无法发生,是否应该抛出并处理它?

C# 如果异常无法发生,是否应该抛出并处理它?,c#,validation,exception-handling,C#,Validation,Exception Handling,我有一个函数,它接受三个参数(日、月和年),并创建一个新的日期时间。它是一个公共函数,当三个组合框中的任何一个被下拉时都会被调用 当单元测试时,我意外地输入了一个无效的值,它抛出了一个无效的日期时间异常,但这在应用程序中是不可能的,因为组合框只预先填充了有效的值 所以问题是,我是否仍应在函数中检查并处理此异常?您不应阻止或捕获此异常。但你应该确保在这种“不可能”的情况下确实会发生异常 例外情况是指被认为“正常”情况下不可能发生的“不可能”情况 例如,如果调用DateTime构造函数重载,那么如果

我有一个函数,它接受三个参数(日、月和年),并创建一个新的日期时间。它是一个公共函数,当三个组合框中的任何一个被下拉时都会被调用

当单元测试时,我意外地输入了一个无效的值,它抛出了一个无效的日期时间异常,但这在应用程序中是不可能的,因为组合框只预先填充了有效的值


所以问题是,我是否仍应在函数中检查并处理此异常?

您不应阻止或捕获此异常。但你应该确保在这种“不可能”的情况下确实会发生异常

例外情况是指被认为“正常”情况下不可能发生的“不可能”情况


例如,如果调用
DateTime
构造函数重载,那么如果输入无效,该构造函数将已经抛出异常。如果你认为这种情况不会发生,不要处理这种情况。框架生成的异常消息很好

您不应该阻止或捕获异常。但你应该确保在这种“不可能”的情况下确实会发生异常

例外情况是指被认为“正常”情况下不可能发生的“不可能”情况


例如,如果调用
DateTime
构造函数重载,那么如果输入无效,该构造函数将已经抛出异常。如果你认为这种情况不会发生,不要处理这种情况。框架生成的异常消息很好

是,如果函数单独允许提交无效输入,则该函数应为无效输入引发异常。您不知道未来的开发人员如何或从何处调用此函数。但另一个更好的选择是对函数进行编码,以便只允许有效的输入

您可以通过将输入类型从整数值更改为枚举来实现这一点。创建月份枚举

public enum CalendarMonth {
  NotSet = 0, January = 1, February = 2,
  March = 3, April = 4, May = 5, June = 6,
  July = 7, August = 8, September = 9,
  October = 10, November = 11, December = 12}
public enum DayOfMonth {
  NotSet = 0, dom1 = 1, dom2 = 2, ....etc., ... dom31 = 31 }
还有一个月的第二天

public enum CalendarMonth {
  NotSet = 0, January = 1, February = 2,
  March = 3, April = 4, May = 5, June = 6,
  July = 7, August = 8, September = 9,
  October = 10, November = 11, December = 12}
public enum DayOfMonth {
  NotSet = 0, dom1 = 1, dom2 = 2, ....etc., ... dom31 = 31 }
您可以对函数进行编码,将其中只有30天的31个月视为下个月的第一个月,将2月29日、30日和31日视为3月1日、2日、3日等,以避免将其视为无效。那么你的函数的签名就是

public DateTime NewDate(DayOfMonth dom, CalendarMonth month, int year);

并且不可能向其传递无效值。(我想除了
DateIme.MinDate
DateTime.MaxDate
范围之外的年份值)

是的,如果函数单独允许提交无效输入,则该函数应该为无效输入抛出异常。您不知道未来的开发人员如何或从何处调用此函数。但另一个更好的选择是对函数进行编码,以便只允许有效的输入

您可以通过将输入类型从整数值更改为枚举来实现这一点。创建月份枚举

public enum CalendarMonth {
  NotSet = 0, January = 1, February = 2,
  March = 3, April = 4, May = 5, June = 6,
  July = 7, August = 8, September = 9,
  October = 10, November = 11, December = 12}
public enum DayOfMonth {
  NotSet = 0, dom1 = 1, dom2 = 2, ....etc., ... dom31 = 31 }
还有一个月的第二天

public enum CalendarMonth {
  NotSet = 0, January = 1, February = 2,
  March = 3, April = 4, May = 5, June = 6,
  July = 7, August = 8, September = 9,
  October = 10, November = 11, December = 12}
public enum DayOfMonth {
  NotSet = 0, dom1 = 1, dom2 = 2, ....etc., ... dom31 = 31 }
您可以对函数进行编码,将其中只有30天的31个月视为下个月的第一个月,将2月29日、30日和31日视为3月1日、2日、3日等,以避免将其视为无效。那么你的函数的签名就是

public DateTime NewDate(DayOfMonth dom, CalendarMonth month, int year);

并且不可能向其传递无效值。(我想除了
DateIme.MinDate
DateTime.MaxDate
范围之外的年份值)

一般来说,是的,任何公共函数都可以从任何地方调用,如果在某个时间点,您确定是谁向函数提供了输入,那么保护代码不受无效输入的影响也是一种很好的做法

然而,如果输入不好,这个假定函数可以自行处理不可能的情况,而不会触发异常

检查输入和遵循众所周知的TryParse模式相对容易

 public bool TryMakeDateTime(int year, int month, int day, out DateTime date)
 {
      date = DateTime.MinValue;

      if(!IsValidDay(year, month, day))
        return false;

      date = new DateTime(year, month, day);
      return true;
 }

 public bool IsValidDay(int year, int month, int day)
 {
     if(day < 1 || day > 31)
        return false;

     if(month < 1 || month > 12)
        return false;

     if(day > 30 && (month == 2 ||
                     month == 4 || 
                     month == 6 || 
                     month == 9 || 
                     month == 11))
        return false;

     // This is arbitrary, adjust the check to your constraints
     if(year < 1900 || year > 2099)
         return false;

     if(month == 2)
     {
         // IsLeapYear cannot handle values below 1 or higher than 9999
         // but we have already checked the year with more retrictive
         // constraints.
         int extraDay = (DateTime.IsLeapYear(year) ? 1 : 0);
         if(day > (28 + extraDay))
             return false;
     }
     return true;
 }
public bool TryMakeDateTime(int年、int月、int日、out DateTime日期)
{
date=DateTime.MinValue;
如果(!IsValidDay(年、月、日))
返回false;
日期=新日期时间(年、月、日);
返回true;
}
公共bool IsValidDay(整数年、整数月、整数日)
{
如果(第1天|第31天)
返回false;
如果(月<1 | |月>12)
返回false;
如果(天>30&(月==2||
月份==4 | |
月份==6 | |
月份==9 | |
月份==11)
返回false;
//这是任意的,请根据您的约束调整检查
如果(年份<1900 | |年份>2099)
返回false;
如果(月份==2)
{
//IsLeapYear无法处理低于1或高于9999的值
//但是我们已经用更多的回击来检查这一年
//限制。
int extraDay=(DateTime.IsLeapYear(year)?1:0;
如果(天>(28天+额外天))
返回false;
}
返回true;
}

一般来说,是的,任何公共函数都可以从任何地方调用,如果在某个时间点,您确定是谁向函数提供了输入,那么保护代码不受无效输入的影响也是一种很好的做法

然而,如果输入不好,这个假定函数可以自行处理不可能的情况,而不会触发异常

检查输入和遵循众所周知的TryParse模式相对容易

 public bool TryMakeDateTime(int year, int month, int day, out DateTime date)
 {
      date = DateTime.MinValue;

      if(!IsValidDay(year, month, day))
        return false;

      date = new DateTime(year, month, day);
      return true;
 }

 public bool IsValidDay(int year, int month, int day)
 {
     if(day < 1 || day > 31)
        return false;

     if(month < 1 || month > 12)
        return false;

     if(day > 30 && (month == 2 ||
                     month == 4 || 
                     month == 6 || 
                     month == 9 || 
                     month == 11))
        return false;

     // This is arbitrary, adjust the check to your constraints
     if(year < 1900 || year > 2099)
         return false;

     if(month == 2)
     {
         // IsLeapYear cannot handle values below 1 or higher than 9999
         // but we have already checked the year with more retrictive
         // constraints.
         int extraDay = (DateTime.IsLeapYear(year) ? 1 : 0);
         if(day > (28 + extraDay))
             return false;
     }
     return true;
 }
public bool TryMakeDateTime(int年、int月、int日、out DateTime日期)
{
date=DateTime.MinValue;
如果(!IsValidDay(年、月、日))
返回false;
日期=新日期时间(年、月、日);
返回true;
}
公共bool IsValidDay(整数年、整数月、整数日)
{
如果(第1天|第31天)
返回false;
如果(月<1 | |月>12)
返回false;
如果(天>30&(月==2||
月份==4 | |
月份==6 | |
月份==9 | |
月份==11)
返回false;
//这个