C# 无参数渔获物与其他渔获物的差异

C# 无参数渔获物与其他渔获物的差异,c#,exception,exception-handling,C#,Exception,Exception Handling,我有一段代码 //Code 1 Code 2 Code 3 try try try { { { //Exp occur //

我有一段代码

//Code 1                        Code 2                          Code 3
try                             try                             try
{                               {                               {
    //Exp occur                     //Exp occur                     //Exp occur 
}                               }                               }
catch (Exception e)             catch (Exception)               catch
{                               {                               {
    //Handle exp                    //Handle exp                    //Handle exp
}                               }                               }
三种代码之间的区别是什么

P.S.我不熟悉
C#
,就
Java
Objective-C
而言,如果您计划实际使用exception对象,此语法会引发错误,要将其属性记录到日志文件中,或显示消息框,或引发另一种异常并将当前异常传递给其构造函数,则必须使用三个异常中的第一个(最左边的一个)


一般来说,最常用的方法是第一种方法,如果你想单独处理不同类型的异常,你可以有多个catch块,从最专门的块开始,在底部有一个你写的块,这样所有没有处理的异常都会以通用catch块结束。

。它们都捕获可能发生的每个异常(通过捕获基本类型
异常
或任何异常)。这通常是不赞成的,理由很充分。您应该按照预期的顺序捕获特定异常,然后如果确实要捕获所有异常,请在末尾捕获
Exception

try
{
}
catch (MyCustomException)
{
    // do something for your custom exception
}
catch (Exception)
{
    // do something for everything else
}
为异常指定变量时,例如
catch(exception e)
,您可以通过
e.Property
或简单地
e.ToString()
访问堆栈跟踪(和其他异常信息),以获取完整消息。捕获异常时抛出异常也是最佳做法(除非您希望在此级别抑制异常,并且不允许调用代码看到异常),这样它会冒泡并保留堆栈跟踪:

catch (Exception e)
{
    // do something with e

    throw;
}

代码1-相当正常的捕获,希望不需要解释

代码2—当发生特定异常时,您希望执行特定的代码段,但您并不打算实际与异常对象交互。应该几乎总是有一个
抛出语句,以便堆栈中更高级别的关心它的其他人可以
捕获它

代码3-您希望代码针对任何异常(*)执行(相同try的早期catch子句捕获的异常除外)。同样,应该几乎总是包含一个
抛出
以便更高的代码可以捕获并实际处理异常


在某个级别(可能只是在顶层,在您所处的任何环境的未处理异常处理程序中),应该检查异常对象并可能记录它(如果可能)。

如果要使用变量“e”获取异常消息、行或类型,请参见此处

//Code 1                       
try                            
{                              
 //Exp occur                
}                              
catch (Exception e)            
{                              
 //Handle exp               
}
下面的代码用于获取特定类型的异常,而不是处理异常变量

//Code 2
try                            
{                              
  //Exp occur                
}                              
catch (Exception)
{                              
 //Handle exp           
}
下面是捕获所有类型异常的代码

//Code 3
try
{
 //Exp occur    
}     
catch 
{                  
 //Handle exp   
}
    try
    {
     //mycode
    }catch(MyException myExc)
    {   
    //TODO HERE  
    Console.Write(myExc.Message);  
    }

代码1

它在对象
e
中捕获异常,该对象稍后可用于异常处理。例如,您可以使用
e.Message
e.StackTrace
记录消息属性或查看堆栈跟踪

代码2

您正在捕获基类型的所有异常
exception
,但由于没有任何与之相关的对象,因此只能抛出该异常,以便它冒泡出现,或者可以忽略该异常。如果在该代码中您有:

catch(InvalidCastException)
然后将在块中处理所有
InvalidCastException
,而不处理异常对象

代码3

您正在捕获所有类型的异常,而不考虑它们的类型,这与基类为
Exception
的代码2类似

尽管catch子句可以在没有参数的情况下用于捕获任何 异常类型,不建议使用此用法。总的来说,你 应该只捕获那些您知道如何从中恢复的异常

如果在捕获基本异常之前捕获特定异常,效果总是更好。差不多

try
{
}
catch(InvalidCastException ex)
{
}
catch(Exception ex)
{
}

在同一个语句中可以使用多个特定catch子句 试试catch语句。在本例中,catch子句的顺序为 这很重要,因为catch子句是按顺序检查的。赶上 在不太具体的异常之前先出现更具体的异常。编译程序 如果您对catch块进行排序,以便稍后的块 永远联系不到


代码1捕获每个异常(在您的情况下!)并声明它,以便您以后可以使用它,例如用于错误消息

MessageBox.Show(e.Message);
代码2还捕获每个异常(在您的情况下!),但您不能使用它,因为它没有声明

这两个方法不是为此而设计的,它们是为捕获特定或自定义异常而设计的

//Code 3
try
{
 //Exp occur    
}     
catch 
{                  
 //Handle exp   
}
    try
    {
     //mycode
    }catch(MyException myExc)
    {   
    //TODO HERE  
    Console.Write(myExc.Message);  
    }
第三个捕获所有异常。因为没有定义

看看:

要了解有关C#差异中异常的更多信息,请执行以下操作:

  • 声明异常参数ex允许您访问异常对象,以便查看和使用其属性、字段、方法等。此“ex”变量的工作方式与任何方法中的任何参数类似

  • 声明不带参数ex的异常类型允许您为不同类型的异常分隔多个“捕获”区域。它是无用的,在功能上等同于您在这里定义的代码示例3,但是如果您需要根据异常的类型执行不同的操作,并且不需要访问异常对象(您只需要知道异常的类型),那么这就是您的方法

  • 无类型捕获异常处理程序允许您为可能引发的任何异常添加回退,无论其类型如何。但是,由于它没有参数化,因此您将无法访问异常对象的属性或方法。因此,代码示例2和代码示例3都是