我在C#中对泛型进行了一些实验,我遇到了一个问题,我希望将泛型类型作为带有约束的类型参数传递,以实现我不知道的类型的泛型接口。
以下是我的例子:
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
namespace ConsoleApplication3
{
class Program
{
interface IGenericCollection<T>
{
IEnumerable<T> Items { get; set; }
}
abstract class GenericCollection<T> : IGenericCollection<T>
{
public IEnumerable<T> Items { get; set; }
}
//This class holds a generic collection but i have to ensure this class
//implements my IGenericCollection interface. The problem here is that
//i dont know which type TGenericCollection is using and so i am unable to
//pass this information to the constraint.
class CollectionOwner<TGenericCollection>
where TGenericCollection : IGenericCollection< dont know ... >
{
protected TGenericCollection theCollection = default(TGenericCollection);
}
static void Main(string[] args)
{
}
}
}
我在这里看过几篇帖子,由于C#和CLR的限制,所有人都告诉我这是不可能的。但是这样做的正确方法是什么?
答案 0 :(得分:1)
也许您应该使用其他类型参数:
class CollectionOwner<TGenericCollection, T2>
where TGenericCollection : IGenericCollection<T2>
where T2 : class
{
protected TGenericCollection theCollection = default(TGenericCollection);
}
这适合你需要吗?
答案 1 :(得分:1)
我认为这里没有问题,只需在您的所有者类中添加另一个通用参数:
class CollectionOwner<T,TGenericCollection>
where TGenericCollection : IGenericCollection<T>
{
protected TGenericCollection theCollection = default(TGenericCollection);
}
答案 2 :(得分:1)
您可以将第二个通用参数添加到实现类中。下面的静态Example
方法显示了此示例。
public interface ITest<T>
{
T GetValue();
}
public class Test<T, U> where T : ITest<U>
{
public U GetValue(T input)
{
return input.GetValue();
}
}
public class Impl : ITest<string>
{
public string GetValue()
{
return "yay!";
}
public static void Example()
{
Test<Impl, string> val = new Test<Impl,string>();
string result = val.GetValue(new Impl());
}
}
答案 3 :(得分:0)
使用第二个通用参数是一个选项4肯定我已经想要使用但是这个
abstract class GenericCollection<T> : IGenericCollection<T>
{
public IEnumerable<T> Items { get; set; }
}
class ConcreteCollection : GenericCollection<string>
{
}
static void Main(string[] args)
{
// will constraint fail here ?
CollectionOwner<int,ConcreteCollection> o = new CollectionOwner(int, ConcreteCollection);
}