子类构造函数异常离开父类实例

时间:2010-11-23 19:55:36

标签: c# inheritance exception-handling

很抱歉要阅读很多代码。这是显示问题的最简单方法。

using System;
using System.Collections.Generic;

namespace P1
{
    class A
    {
        static Dictionary<int, A> a = new Dictionary<int, A>();
        static int i = 0;

        int id;
        public A()
        {
            id = ++i;
            a[id] = this;
        }

        public static int Count() { return a.Count; }
    }

    class B : A
    {
        public B()
        {
            throw new Exception();
        }
    }

    class Program
    {
        static void Main(string[] args)
        {
            try
            {
                var b = new B();
            }
            catch
            {
               // What should be here ????
            }

            Console.WriteLine(A.Count()); //prints 1 - not good
            Console.ReadKey();
        }
    }
}

当子类构造函数失败时,是否有人可以建议清理逻辑?

2 个答案:

答案 0 :(得分:1)

您需要将清理逻辑放在B的构造函数中,因为在构造函数失败后您无法访问实例引用。

以下是有关如何执行此操作的示例:

class A
{
    static Dictionary<int, A> a = new Dictionary<int, A>();
    static int i = 0;

    int id;
    public A()
    {
        id = ++i;
        a[id] = this;
    }

    protected void Destroy()
    {
        a.Remove(id);
        i--;
    }

    public static int Count() { return a.Count; }
}

class B : A
{
    public B() 
    {
        try
        {
            throw new Exception();
        }
        catch (Exception)
        {
            Destroy();
            throw;
        }
    }
}

答案 1 :(得分:0)

在抛出异常之前正在调用您的基类构造函数,因此该对象已经被创建并分配到它a中的位置。如果您希望构造函数不创建对象,那么您可能需要考虑静态方法来实例化新的A而不是使用默认构造函数。然后,当对象的实例化失败时(在B中),您将在将对象添加到字典之前抛出异常。