Nait Nait - 23 days ago 9
C# Question

Implicitly convert generic classes

I'm trying to accomplish something like this.

public class GreatClass<A, B>
where A : IA
where B : IB, new()
{
public void Function()
{
var list = new List<A>();
var obj = new B { Items = list.ToArray() };
}
}

public interface IA
{
}

public interface IB
{
IA[] Items { get; set; }
}

namespace Namespace1
{
public class A : IA {}
public class B : IB {}
}

namespace Namespace2
{
public class A : IA {}
public class B : IB {}
}


So I have two namespaces with similar classes which implements the same interface. I have some logic which I want to share between the classes in the two namespaces and am therefore using generic classes which implements the implemented interface.

However I get a compile error on "list.ToArray()" stating that it Cannot implicitly type 'A[]' to 'IA[]'. Is there something I can do which makes the compiler understand how to handle this?

Using .Cast() like a few of you have been suggesting gives me a runtime error instead. That I can't convert type IA[] to Namespace1.A[] (or Namespace2.A[]).

Answer

There are several options, but the best one is to strongly type your B class and make it generic.

This is the code that will do. Note that TA is the type of A you are passing in, thus always allowing to access the members strongly typed.

public interface IB<TA> where TA : IA
{
    TA[] Items { get; set; }
}

And change GreaterClass to this:

public class GreatClass<A, B>
    where A : IA
    where B : IB<A>, new()
{
}