如何防止派生类多次初始化属性

时间:2016-08-30 19:17:21

标签: c# oop inheritance

以下代码是简短的"摘要"我的真实项目,只包含相关部分,以了解我的问题。 (并且不想用原始代码破坏某人的某一天)。

想象你有4个班级:分部,分部,部门和团队。每个类都按该顺序继承基类。

最终目标:返回一个分区对象,其中包含7个分支列表,每个分支包含7个部门的列表,每个部门包含7个团队的列表。 例如,我将能够从外部到达每个类实例:

division d = new division();
d.CreateDivisionStructure();
int Example = d.ListOfBranches[5].ListOfDepartments[4].ListOfTeam[3].SomeIntegerProperty;

(原始代码列出,覆盖函数,属性等。)

问题:想象下面代码中的protected string _myVarDatatable,需要通过myVar属性初始化资源消耗大量的SQL查询。因此,我希望只为一次“{1}}初始化{34}分区单位结构"”。在下面的代码protected string _myVar中将为空64次并将初始化64次(对于我的理解,每个单元7次,每次protected string _myVar次调用一次)。

我怎样才能实现这一目标?

我尝试了很多其他方法,但无法解决这个问题。我会感谢任何帮助,不同的思考方式或建议。

base()

3 个答案:

答案 0 :(得分:2)

这可能很好地利用了Lazy<T>类,在静态变量中使用,因此该进程只有一个副本。在第一次访问变量时,它将运行一次Func初始化。

https://msdn.microsoft.com/en-us/library/dd642331(v=vs.110).aspx

但是,根据您的班级结构,我不确定它是否是最好的方法。 Branch : divisionDepartment : Branch层次结构的目的是什么。 BranchDivision吗?如果您尝试共享公共属性而不再对其进行编码,我建议您创建一个公共类,该类可以保存BranchDivisionDepartment可以继承的变量

答案 1 :(得分:1)

您可以在层次结构中的最低类中使用静态变量/静态构造函数。静态构造函数只会被调用一次。

答案 2 :(得分:1)

一个简单的解决方案是使用“控制”变量 我相信你可以改进你的设计并避免这个问题,但我现在没有时间检查它..

using System;

namespace Program
{
    internal class Program
    {
        private static void Main(string[] args)
        {
            division d = new division();
            d.CreateDivisionStructure();

            Console.ReadLine();
        }
    }

    internal class division

    {
        private static int CountHowManyTimesMyVarWasInitilized = 0;

        public division()

        {
        }

        protected string _myVar;
        private bool _isReadyForInitialization;
        public string myVar
        {
            get
            {
                if (!_isReadyForInitialization)
                    return null;
                if (_myVar == null)
                {

                    CountHowManyTimesMyVarWasInitilized++;
                    Console.WriteLine(CountHowManyTimesMyVarWasInitilized);
                    _myVar = "now myVar is not null";
                    return _myVar;
                }
                else
                { return _myVar; }
            }
            set { _myVar = value; }
        }

        public void CreateDivisionStructure()

        {
            // now _myVar is spposed to be initilized to all dirved clasess isnt is?
            Console.WriteLine(myVar);
            for (int i = 0; i < 7; i++)
            {
                Branch b = new Branch(7);
            }
            _isReadyForInitialization = true;
            Console.WriteLine(myVar);
        }
    }

    internal class Branch : division

    {
        public Branch(bool dImDerivedClass)
        {
            //  constructor for department to prevent recursive stackoverflow if base of department will call the empty constructor
        }

        public Branch(int NumberOfBranches)
        {
            Console.WriteLine(myVar);
            Department d = new Department(7);
        }
    }

    internal class Department : Branch

    {
        public Department(bool ImDerivedClass) : base(true)
        {
            //  constructor for team to prevent recursive stackoverflow if base of Team will call the empty constructor
        }

        public Department(int numberOfDep) : base(true)
        {
            for (int i = 0; i < numberOfDep; i++)
            {
                Console.WriteLine(myVar);
                Team t = new Team(7);
            }
        }
    }

    internal class Team : Department

    {
        public Team():base(false)
        {

        }
        public Team(int numberOfTeams) : base(true)
        {
            for (int i = 0; i < numberOfTeams; i++)
            {
                Console.WriteLine(myVar);
            }
        }
    }
}