【发布时间】:2014-06-27 17:49:55
【问题描述】:
在一次面试中,面试官问了我这个问题。 我们可以在基类中捕获子类方法抛出的异常吗? 我说不,但他说是的,这是可能的。 所以我想知道这是否可能,如果是,请给我任何实际的例子。 您不必调用基类方法。 谢谢。
【问题讨论】:
-
在什么情况下?如果您的意思是直接覆盖的虚拟方法,那么基类无法捕获子实现中抛出的异常。
标签: c#
在一次面试中,面试官问了我这个问题。 我们可以在基类中捕获子类方法抛出的异常吗? 我说不,但他说是的,这是可能的。 所以我想知道这是否可能,如果是,请给我任何实际的例子。 您不必调用基类方法。 谢谢。
【问题讨论】:
标签: c#
这是一个简单的示例,其中基类从派生类捕获异常。
abstract class Base
{
// A "safe" version of the GetValue method.
// It will never throw an exception, because of the try-catch.
public bool TryGetValue(string key, out object value)
{
try
{
value = GetValue(key);
return true;
}
catch (Exception e)
{
value = null;
return false;
}
}
// A potentially "unsafe" method that gets a value by key.
// Derived classes can implement it such that it throws an
// exception if the given key has no associated value.
public abstract object GetValue(string key);
}
class Derived : Base
{
// The derived class could do something more interesting then this,
// but the point here is that it might throw an exception for a given
// key. In this case, we'll just always throw an exception.
public override object GetValue(string key)
{
throw new Exception();
}
}
【讨论】:
给你:
public class BaseClass
{
public void SomeMethod()
{
try
{
SomeOtherMethod();
}
catch(Exception ex)
{
Console.WriteLine("Caught Exception: " + ex.Message);
}
}
public virtual void SomeOtherMethod()
{
Console.WriteLine("I can be overridden");
}
}
public class ChildClass : BaseClass
{
public override void SomeOtherMethod()
{
throw new Exception("Oh no!");
}
}
SomeMethod,定义在基类上,调用同一对象的另一个方法SomeOtherMethod 并捕获任何异常。如果您在某个子类中覆盖 SomeOtherMethod 并引发异常,那么这将在基类上定义的 SomeMethod 中捕获。您的问题中使用的语言有点模棱两可(从技术上讲,在运行时它仍然是 ChildClass 执行异常处理的实例),但我认为这就是您的面试官所了解的。
另一种可能性(同样,取决于解释)是基类的实例调用继承所述基类的不同对象的方法,该方法抛出异常(然后捕获例外):
public class BaseClass
{
public void SomeMethod()
{
var thing = new ChildClass();
try
{
thing.ThrowMyException();
}
catch(Exception ex)
{
Console.WriteLine("Exception caught: " + ex.Message);
}
}
}
public class ChildClass : BaseClass
{
public void ThrowMyException()
{
throw new Exception("Oh no!");
}
}
这里,当BaseClass.SomeMethod 被调用时,一个基类的实例捕获一个子类另一个实例中抛出的异常。
【讨论】: