I have a list of objects with the same base class. These objects can be constructed from multiple places but only exist as part of such a list. When adding a new object, I want to check if an object of the same class is already in its parent list. I’ve tried to do this as follows:
public class ListHolder
{
List<BaseType> a = new List<BaseType>();
}
public abstract class BaseType
{
public BaseType(ListHolder listIn)
{
if (listIn.a.OfType<typeof(this)>().Any())
{
listIn.a.OfType<typeof(this)>().ToList()[0].Reapply();
} else {
listIn.Add(this);
Apply();
}
}
protected abstract void Reapply();
protected abstract void Apply();
}
This does not work; I get a series of syntax errors, I’m guessing because OfType doesn’t like having to calculate typeof inside its call. It also doesn’t work to say Type t = typeof(this) and then call OfType< t>. How can I get around this?
EDIT:
I’d like to be able to then call something like
public class DerivedType : BaseType
{
protected override void Reapply() {}
protected override void Apply() {}
}
ListHolder b = new ListHolder();
b.a.Add((BaseType)Activator.CreateInstance(DerivedType)); // Should call Apply
b.a.Add((BaseType)Activator.CreateInstance(DerivedType)); // Should call Reapply
o wait adding to list is in the constructor in this example… well you get the gist
>Solution :
Instead of using OfType<T>(), which takes a generic parameter (which is required at compile time), you can just check if any element is the same type as this.GetType() (which is done at runtime), since this.GetType() refers to the child class’ type, not the parent’s:
public abstract class BaseType
{
public BaseType(ListHolder listIn)
{
// Find the first element of the (child's) type
var element = listIn.a.FirstOrDefault(element => element.GetType() == this.GetType());
if (element != null)
{
element.Reapply();
}
else
{
listIn.a.Add(this);
Apply();
}
}
protected abstract void Reapply();
protected abstract void Apply();
}
Testing with two child classes A and B:
public class A : BaseType
{
public A(ListHolder listIn) : base(listIn) { }
protected override void Reapply()
{
Console.WriteLine("A reapply");
}
protected override void Apply()
{
Console.WriteLine("A apply");
}
}
public class B : BaseType
{
public B(ListHolder listIn) : base(listIn) { }
protected override void Reapply()
{
Console.WriteLine("B reapply");
}
protected override void Apply()
{
Console.WriteLine("B apply");
}
}
public static void Main()
{
ListHolder holder = new();
new A(holder);
new B(holder);
new B(holder);
new A(holder);
}
results in:
A apply
B apply
B reapply
A reapply