C# 我是否可以在运行时为OrderBy实例化IComparer类,而不考虑其类型?
有人知道这是否可能吗?我有一个自定义属性类,它定义了一个为属性实现IComparer的类型。我希望通过反射访问该类型,并将其实例化以在IEnumerable.OrderBy()中使用: 由于C# 我是否可以在运行时为OrderBy实例化IComparer类,而不考虑其类型?,c#,reflection,ienumerable,C#,Reflection,Ienumerable,有人知道这是否可能吗?我有一个自定义属性类,它定义了一个为属性实现IComparer的类型。我希望通过反射访问该类型,并将其实例化以在IEnumerable.OrderBy()中使用: 由于OrderBy要求第二个参数的类型为IComparer(编译时未知),因此无法编译上述参数 是否有方法使用“property”中的类型信息实例化“insta”变量并将其转换为IComparer 编辑: 第一个选项让我非常接近: Func<ResultViewModel, PropertyInfo>
OrderBy
要求第二个参数的类型为IComparer
(编译时未知),因此无法编译上述参数
是否有方法使用“property”中的类型信息实例化“insta”变量并将其转换为IComparer
编辑:
第一个选项让我非常接近:
Func<ResultViewModel, PropertyInfo> sel = t => property;
this.Results = infoGeneric.Invoke(Results, new object[] { vals, sel, insta }) as IEnumerable<ResultViewModel>;
RuntimePropertyInfo似乎是内部的。。。是否有其他方法传入属性选择器?基本上,您有两个选项:
- 同样使用反射调用
:获取泛型方法定义,然后调用以获取构造的版本,然后调用它OrderBy
- 在C#4中使用
,让内置的迷你编译器为您完成繁重的工作dynamic
property.GetValue()
只返回object
,因此几乎肯定要通过反射路径。或者你可以用第三个,在某个可怕但非常简单的地方
。。。让所有比较器实现IComparer
,并在其中强制转换。然后您的TResult
将是对象
,您可以直接强制转换:
object tmp = Activator.CreateInstance(sortComparer.ComparerType);
IComparer<object> comparer = (IComparer<object>) tmp;
this.Results = lstResults.Select(r => new ResultViewModel(r))
.OrderBy(p => property.GetValue(p, null), comparer);
object tmp=Activator.CreateInstance(sortComparer.ComparerType);
IComparer comparer=(IComparer)tmp;
this.Results=lstreults.Select(r=>newresultviewmodel(r))
.OrderBy(p=>property.GetValue(p,null),比较器);
有时最好使用函数方法,通过工厂函数实例化帮助器类
- 实现
接口[]的泛型类IComparer
内部类GenericEqualityComparer:IEqualityComparer { 专用只读函数比较器; 公共通用质量比较程序(功能比较程序){ _比较器=比较器; } 公共布尔等于(TX,TY) { 返回比较器(x,y); } 公共int GetHashCode(T obj) { 返回base.GetHashCode(); } }
- 使用工厂方法实例化泛型比较器类[],并将
delegate作为参数传递给该类Func compare
IComparer<Point> comparer = comparator<Point>((a, b) => { return (a.X + a.Y) - (b.X + b.Y); }); comparer.Compare(new Point(0, 0), new Point(0, 0)); // should return zero comparer.Compare(new Point(100, 0), new Point(0, 0)); // should return a value greater than zero comparer.Compare(new Point(0, 0), new Point(100, 0)); // should return a value less than zero
IComparer comparer=比较器((a,b)=> { 回报率(a.X+a.Y)-(b.X+b.Y); }); comparer.Compare(新点(0,0),新点(0,0));//应该返回零 comparer.Compare(新点(100,0),新点(0,0));//应返回大于零的值 comparer.Compare(新点(0,0),新点(100,0));//应返回小于零的值
object tmp = Activator.CreateInstance(sortComparer.ComparerType);
IComparer<object> comparer = (IComparer<object>) tmp;
this.Results = lstResults.Select(r => new ResultViewModel(r))
.OrderBy(p => property.GetValue(p, null), comparer);
internal class GenericEqualityComparer<T> : IEqualityComparer<T>
{
private readonly Func<T, T, bool> _comparer;
public GenericEqualityComparer(Func<T, T, bool> comparer) {
_comparer = comparer;
}
public bool Equals(T x, T y)
{
return _comparer(x, y);
}
public int GetHashCode(T obj)
{
return base.GetHashCode();
}
}
IComparer<Point> comparer = comparator<Point>((a, b) =>
{
return (a.X + a.Y) - (b.X + b.Y);
});
comparer.Compare(new Point(0, 0), new Point(0, 0)); // should return zero
comparer.Compare(new Point(100, 0), new Point(0, 0)); // should return a value greater than zero
comparer.Compare(new Point(0, 0), new Point(100, 0)); // should return a value less than zero