简体   繁体   中英

C# Make a List to hold any derived children of a base class

So I wish to setup an abstract base class to derive children classes from. All the work will take place on the children, but I wanted the children to be able to reference each other.

Here is some pseudo-code:

public abstract class BaseClass<T> : SomeOtherClass {

    public List<BaseClass> listOfChildren;

    protected T thisChild;

    public void DoMoreStuff(){
        Debug.Log("Doing more stuff");
    }

    protected virtual void DoSomething(int i){
        listOfChildren[i].DoMoreStuff();
    }
}

public class FirstChildClass : BaseClass<FirstChildClass> {

    FirstChildClass<T>(){
        thisChild = this;
    }

    public void FirstClassStuff(){
        Debug.Log("first class stuff");
    }

}
public class SecondChildClass : BaseClass<SecondChildClass> {

    public void SecondClassStuff(){
        Debug.Log("second class stuff");
    }
}

How would I make a generic List to accept any child class?

Will I need to typecast listOfChildren with T to use DoMoreStuff()?

On its own, is there anything else inherently wrong with this setup?

I think you overcompicate the solution. If you don't want to store any data in each node - try to solve this problem then without the generics. I will give you a naive straight-forward implementation of desired behavior as a starting point.

public abstract class BaseClass  {

    private IList<BaseClass> children = new List<BaseClass>();

    public void AddChild(BaseClass child)
    {
        this.children.Add(child);
    }

    protected virtual void DoMoreStuff(){
        Debug.Write("Doing more stuff");
    }

    public void DoSomething(int i){
        children[i].DoMoreStuff();
    }
}

public class FirstChildClass : BaseClass {

    protected override void DoMoreStuff(){
        Debug.Write("first class more stuff");
    }

}

public class SecondChildClass : BaseClass {

    protected override void DoMoreStuff(){
        Debug.Write("second class more stuff");
    }
}

now you can

var root = new FirstChildClass();

root.AddChild(new FirstChildClass());
root.AddChild(new SecondChildClass());
root.AddChild(new FirstChildClass());

root.DoSomething(1); //will print second class more stuff
root.DoSomething(0); //will print first class more stuff

You need to separate between child classes and child data . A child class simply inherits from its parent, to provide a more detailed structure to the data (such as Animal and Dog ). A child data, on the other hand, means that whatever the data represents is related to each other (such as Receipt and ReceiptLineItem ).

Normally, the two don't overlap. The Receipt class looks nothing like the ReceiptLineItem class, and the Receipt and a ExternalPurchaseOrder have nothing to do with each other, even though they both inherit their structure from Purchase . When they do overlap, you have a tree structure. A Product may be composed of more Product s, which each may be composed of yet more Product s.


Here's how I'd rewrite your code, assuming you're looking for the first type of inheritance (class structure):

public abstract class BaseClass : SomeOtherClass {

    public static List<BaseClass> listOfChildren = new List<BaseClass>();

    public void DoMoreStuff(){
        Debug.Log("Doing more stuff");
    }

    protected virtual void DoSomething(int i){
        listOfChildren[i].DoMoreStuff();
    }
}

public class FirstChildClass : BaseClass {

    FirstChildClass(){
       // Set some things unique to this class
    }

    public void FirstClassStuff(){
        Debug.Log("first class stuff");
    }

}
public class SecondChildClass : BaseClass<SecondChildClass> {

    public void SecondClassStuff(){
        Debug.Log("second class stuff");
    }
}

You could then access the master list as BaseClass.listOfChildren . If you want all children to automatically register themselves, you can add that to the BaseClass constructor:

protected BaseClass()
{
   listOfChildren.Add(this);
}

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM