2015-10-27 18 views
1

System.Exception类有4个构造函数:为什么在C#Exception类没有带有1个异常参数的构造函数?

public Exception(); 
public Exception(string message); 
protected Exception(SerializationInfo info, StreamingContext context); 
public Exception(string message, Exception innerException); 

为什么它没有这个构造?

public Exception(Exception innerException); 


这是一个地方,这将是有帮助的。

我有一个静态方法来得到一个开放的连接:

public static DbConnection GetOpenConnection(string dataProvider, string connectionString) 
{ 
    DbConnection dbConnection = GetDbProviderFactory(dataProvider).CreateConnection(); 
    dbConnection.ConnectionString = connectionString; 
    dbConnection.Open(); 
    return dbConnection; 
} 

我想这个方法抛出一个自定义异常GetOpenConnectionException如果有错误发生。

因此,我创建了自定义异常GetOpenConnectionException

public class GetOpenConnectionException : Exception 
{ 
    public GetOpenConnectionException(string message) : base(message) 
    { 
    } 
    public GetOpenConnectionException(string message, Exception innerException) : base(message, innerException) 
    { 
    } 
} 

由于Exception没有构造public Exception(Exception innerException),我不能有这样的代码在GetOpenConnectionException

public GetOpenConnectionException(Exception innerException) : base(innerException) 
{ 
} 

所以我不得不来编码GetOpenConnection()这种方法:

public static DbConnection GetOpenConnection(string dataProvider, string connectionString) 
{ 
    try 
    { 
     DbConnection dbConnection = GetDbProviderFactory(dataProvider).CreateConnection(); 
     dbConnection.ConnectionString = connectionString; 
     dbConnection.Open(); 
     return dbConnection; 
    } 
    catch (Exception e) 
    { 
     throw new GetOpenConnectionException("", e); 
    } 
} 

我想要的东西是这样的编码方法GetOpenConnection()

public static DbConnection GetOpenConnection(string dataProvider, string connectionString) 
{ 
    try 
    { 
     DbConnection dbConnection = GetDbProviderFactory(dataProvider).CreateConnection(); 
     dbConnection.ConnectionString = connectionString; 
     dbConnection.Open(); 
     return dbConnection; 
    } 
    catch (Exception e) 
    { 
     throw new GetOpenConnectionException(e); 
    } 
} 

这是否有道理?

+4

任何原因,你不能只是做'public GetOpenConnectionException(Exception innerException):base(“”,innerException)'' –

+4

基本上你只是在另一个异常中包装一个异常,添加一条消息有助于说明为什么要包装它,否则只是重新抛出内部异常。如果您没有为异常增加价值,请不要包装它。 –

+0

通过在此处重新抛出异常,您获得了什么? –

回答

1

其他答案提供了很好的方法来实现你所要求的,但我相信你的问题的核心是:“为什么这不存在呢?”

当例程关于它使用的资源的假设或先决条件以及它所要求的参数未得到满足时,通常会抛出异常。抛出的异常应该有助于调用者(或程序员)理解不符合什么假设或先决条件,以便他们能够相应地处理或修复他们的代码。该信息是该通信的重要组成部分。我甚至会冒险猜测,如果Exception类不需要可序列化,那甚至不会有空的构造函数!

在另一个嵌套异常意味着嵌套的异常是容器异常的原因。 (Exception类的特定构造函数的documentation指向了这一点。)如果仅仅传递一个没有任何消息的内部异常,就会有效地转化为“我将抛出一个异常,除了它的类型外,它不提供额外的信息。“这不是非常有帮助,它很可能已经更好简单地让原来的异常被抛出

这里是你能提供一个更有意义的信息的一种方式。

public static DbConnection GetOpenConnection(string dataProvider, string connectionString) 
{ 
    try 
    { 
     DbConnection dbConnection = GetDbProviderFactory(dataProvider).CreateConnection(); 
     dbConnection.ConnectionString = connectionString; 
     dbConnection.Open(); 
     return dbConnection; 
    } 
    catch (Exception e) // consider changing this to a more specific type of exception, as an error with .Open() is not the only way it could fail 
    { 
     // provide a meaningful message to the caller about the context of this error 
     var message = string.Format("An error occurred while trying to connect to the data provider {0} with the connection string {1}.", dataProvder, connectionString); 
     throw new GetOpenConnectionException(message, e); 
    } 
} 
+0

谢谢。 “为什么这首先不存在?”真的是我的问题,你已经完全回答了。 – ChumboChappati

4
public GetOpenConnectionException(Exception innerException) : base("", innerException) 
    { 
    } 
+4

虽然此代码可能会回答问题,但为何和/或代码如何回答问题提供了其他上下文,这可以提高其长期价值。 – ryanyuyu

+0

在此清除异常消息。如果你试图获得ex.Message,你总会得到一个空字符串。 – CharithJ

+0

也许':base(null,innerException)'更好? –

0

到彼得·多瑞的回答一样,你可以这样做:

public GetOpenConnectionException(Exception innerException) : 
    base(innerException.message, innerException) 
{ 
} 

这样你实际上是通过一些有意义的东西到基本构造。

至于为什么没有一个构造函数只接受一个Exception参数......它似乎并不是一个很好的理由。他们很容易拥有。

相关问题