我想我过去在C ++(在我的问题历史记录中找不到它)的上下文中问过这个问题,解决方法是使用模板函数。当C ++模板在编译时解析时,它可以工作。但是对于C#,它没有。
public Hashtable ConvertToHashtable<T>(T source) where T has an index operator
{
Hashtable table = new Hashtable();
table["apple"] = source["apple"];
return table;
}
目前的一个用法是将OleDbReader中的结果转换为哈希表,但我很快就会想到更多源类型。
答案 0 :(得分:2)
您可以使用界面:
public interface IIndexable<T> {
T this[int index] { get; set; }
T this[string key] { get; set; }
}
您的方法如下:
public Hashtable ConvertToHashtable<T>(T source)
where T : IIndexable<T> {
Hashtable table = new Hashtable();
table["apple"] = source["apple"];
return table;
}
一个简单的来源是:
public class Source : IIndexable<Source> {
public Source this[int index] {
get {
// TODO: Implement
}
set {
// TODO: Implement
}
}
public Source this[string key] {
get {
// TODO: Implement
}
set {
// TODO: Implement
}
}
}
一个简单的消费者是:
public class Consumer{
public void Test(){
var source = new Source();
var hashtable = ConvertToHashtable(source);
// you haven't to write: var hashtable = ConvertToHashtable<Source>(source);
}
}
答案 1 :(得分:1)
是否可以添加约束以指定类型参数为IList
?
public Hashtable ConvertToHashtable<T>(T source) where T : IList
{
Hashtable table = new Hashtable();
table["apple"] = source["apple"];
return table;
}
Item
属性this[int index]
不是运算符,它是包含类型的属性成员。 IList
暴露了这一点。
答案 2 :(得分:0)
如果运行时检查足够好,您可以使用反射作为评论员之一,如下所示:
if (typeof (T).GetProperties().Any(property => property.Name.Equals("Item")))
答案 3 :(得分:0)
C#中的运算符没有通用type constraints - 这是C#中泛型的限制之一。