匿名IComparer实现

时间:2011-03-13 11:06:04

标签: c#

是否可以定义IComparer的匿名实现?

我相信Java允许内联定义匿名类 - C#?

查看此代码,我想定义一个自定义IComparer内嵌

public static IOrderedEnumerable<TSource> OrderBy<TSource, TKey>(
    this IEnumerable<TSource> source,
    Func<TSource, TKey> keySelector,
    IComparer<TKey> comparer
)

8 个答案:

答案 0 :(得分:32)

如下面的评论之一所示,.Net 4.5通过Comparer&lt;&gt;上的静态方法允许这一点。等级,例如根据类中属性的值比较两个对象:

var comparer = Comparer<KilowattSnapshot>.Create( 
        (k1, k2) => k1.Kilowatt.CompareTo(k2.Kilowatt) );

显然,这可以用于内联而不是分配给变量。

答案 1 :(得分:12)

即使您无法创建实现接口的匿名类,在大多数情况下(例如排序等),您通常可以使用Comparison Delegate而不是IComparer Interface

Array.Sort(arr, (x, y) => 1);

还有一些IComparer的内置实现,例如Comparer ClassStringComparer Class ......

答案 2 :(得分:11)

.NET framework 4.5版提供了方法Comparer.Create(Comparison),用于根据指定的比较委托(可以是lambda函数)创建比较器。然而,使用早期版本的.NET的人可能需要自己实现类似的东西。

答案 3 :(得分:9)

不,C#目前不允许内联接口实现;虽然 允许您通过lambda表达式和匿名方法内联创建委托

在您的情况下,我建议使用ProjectionComparer,以便于使用此功能,例如列出here的功能。

答案 4 :(得分:3)

不,这是不可能的。但是,您可以通过IComparer<TKey>获得Comparer<TKey>.Default的默认实施。否则,您将需要创建一个参数化实现并使用它的实例。

答案 5 :(得分:1)

与Java不同,C#不允许使用内联类匿名内联类实现接口。对于简单的比较(即在单个键上进行比较),有一种更好的方法可以在C#中执行此操作。您可以简单地使用.OrderBy()方法并传入指定密钥的lambda表达式。

using System;
using System.Collections;
using System.Collections.Generic;
using System.Linq;


namespace Test{
    public class Test{
        public static void Main(){
            IList<int> mylist = new List<int>();
            for(int i=0; i<10; i++) mylist.Add(i);
            var sorted = mylist.OrderBy( x => -x );
            foreach(int x in sorted)
                Console.WriteLine(x);
        }
    }
}

答案 6 :(得分:1)

看看这两个问题,他们解决了基本相同的问题

Use of Distinct with list of Custom Object

Wrap a delegate in an IEqualityComparer

如果你这样做,你应该特别注意Slaks的评论和关于哈希码实现的Dan Tao's answer

答案 7 :(得分:0)

Array.Sort(arrayName,(x,y)=&gt; string.Compare(x.Name,y.Name,StringComparison.CurrentCulture));