简体   繁体   中英

Generic objects in c#

i have a litte problem and i need some help :)

For example i have a simle abstract class

public abstract class BaseDefinition
{
    public int Id { get;set; }
    public string Name { get;set; }
}

and other base class

public abstract class BaseParentClass
{
    public string Name { get;set; }
    public string Schema { get;set; }
}

and first generic abstract class

public abstrac class BaseParentClass<T> : 
    BaseParentClass where T : BaseDefinition
{
    public IList<T> Objects {get;set;}
}

and first implementations

public class ClassADefintion : BaseDefinition
{
    public bool IsChanged {get;set;}
}


public class ClassAObject : BaseParentClass<ClassADefinition>
{
     public bool OtherField {get;set;}
}

public class ClassBDefintion : BaseDefinition
{
    public bool IsBBBChanged {get;set;}
}

public class ClassBObject : BaseParentClass<ClassBDefinition>
{
     public bool OtherBBBBField {get;set;}
}

Sorry for class name, but I can't create anything better (it's only example) As We see, now is all OK :).

I have some methods who returns a IEnumerable of generic implementation

IEnumerable<ClassBObject> ClassBObjectCollection;
IEnumerable<ClassAObject> ClassAObjectCollection;

Now i must create a method, who can take a generic objects in IEnumerable

public void DoWork(IEnumerable<BaseParentClass<BaseDefinition>> objects)
{
    foreach(var baseObj in objects)
    {
        foreach(var baseDef in baseObj.Objects)
        {
            // do some work
        }
    }
}

How i remember BaseObject<BaseDefinition> != ClassAObject , but compiler doesn't put on screen any errors. I remember in .NET in generic interface We can use IN and OUT T, so i try make this

public interface IBaseParentClass<out T> where T : BaseDefinition
{
    IList<T> Objects {get;set;}
}

Yup, You can't make a List of <out T> . Somebody have any idea for this problem ?

I can get this fields values by reflection, but i have abstract class and interface so i think is a better way.

I don't have a compiler at hand, but I think it should be possible to rewrite DoWork as such:

public void DoWork<T>(IEnumerable<BaseObject<T>> objects) 
    where T : BaseDefinition
{
    foreach(var baseObj in objects)
    {
        foreach(var baseDef in baseObj.Objects)
        {
            // do some work
        }
    }
}

I am not sure whether the compiler will be able to infer T for you, try it out.

Another possibility may be that if you enumerate those objects anyway, to make Objects of Type IEnumerable(Of T).

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