C#排序/比较项目
发布时间:2020-12-16 00:07:04  所属栏目:百科  来源:网络整理 
            导读:我有一个类(Patch),我想要排序,所以我实现了IComparer. 但是,它需要根据用户的需要进行排序,例如: – key1,key2,key3 – key1,key3,key2 对于每个密钥比较,我写了一个IComparer类,但是,我想知道如何实现它的连接.即排序时我只能传递一个IComparer实例. 或者
                
                
                
            | 
                         
 我有一个类(Patch),我想要排序,所以我实现了IComparer. 
  
  
但是,它需要根据用户的需要进行排序,例如: 对于每个密钥比较,我写了一个IComparer类,但是,我想知道如何实现它的连接.即排序时我只能传递一个IComparer实例. 或者我应该为每种完整排序创建一个IComparer类,即IComparerKey1Key2Key3,IComparerKey1Key3Key2等? 解决方法
 您可以创建一个通用比较器,让代理人选择密钥: 
  
  
  
        class ByKeyComparer<T,TKey> : IComparer<T>
{
    private readonly Func<T,TKey> _keySelector;
    private readonly IComparer<TKey> _keyComparer;
    public ByKeyComparer(Func<T,TKey> keySelector,IComparer<TKey> keyComparer = null)
    {
        if (keySelector == null) throw new ArgumentNullException("keySelector");
        _keySelector = keySelector;
        _keyComparer = keyComparer ?? Comparer<TKey>.Default;
    }
    public int Compare(T x,T y)
    {
        return _keyComparer.Compare(_keySelector(x),_keySelector(y));
    }
} 
 使用帮助器类来利用类型推断(因此您不需要指定键的类型): static class ByKeyComparer<T>
{
    public static IComparer<T> Create<TKey>(Func<T,IComparer<TKey> keyComparer = null)
    {
        return new ByKeyComparer<T,TKey>(keySelector,keyComparer);
    }
} 
 你可以像这样使用它: var patchVersionComparer = ByKeyComparer<Patch>.Create(p => p.Version); patches.Sort(patchVersionComparer); 如果需要组合多个比较键,可以创建一个使用其他比较器的比较器: class CompositeComparer<T> : IComparer<T>
{
    private readonly IEnumerable<IComparer<T>> _comparers;
    public CompositeComparer(IEnumerable<IComparer<T>> comparers)
    {
        if (comparers == null) throw new ArgumentNullException("comparers");
        _comparers = comparers;
    }
    public CompositeComparer(params IComparer<T>[] comparers)
        : this((IEnumerable<IComparer<T>>)comparers)
    {
    }
    public int Compare(T x,T y)
    {
        foreach (var comparer in _comparers)
        {
            int result = comparer.Compare(x,y);
            if (result != 0)
                return result;
        }
        return 0;
    }
} 
 用法示例: var comparer = new CompositeComparer<Patch>(
                       ByKeyComparer<Patch>.Create(p => p.Key1),ByKeyComparer<Patch>.Create(p => p.Key2),ByKeyComparer<Patch>.Create(p => p.Key3));
patches.Sort(comparer); 
 编辑:这是一个更流畅的API: static class ByKeyComparer<T>
{
    public static IComparer<T> CompareBy<TKey>(Func<T,keyComparer);
    }
}
static class ComparerExtensions
{
    public static IComparer<T> ThenBy<T,TKey>(this IComparer<T> comparer,Func<T,IComparer<TKey> keyComparer = null)
    {
        var newComparer = ByKeyComparer<T>.CompareBy(keySelector,keyComparer);
        var composite = comparer as CompositeComparer<T>;
        if (composite != null)
            return new CompositeComparer<T>(composite.Comparers.Concat(new[] { newComparer }));
        return new CompositeComparer<T>(comparer,newComparer);
    }
} 
 例: var comparer = ByKeyComparer<Patch>.CompareBy(p => p.Key1)
                                   .ThenBy(p => p.Key2)
                                   .ThenBy(p => p.Key3);
patches.Sort(comparer); 
 (显然你可能想要添加* CompareBy和ThenBy方法的降序版本以允许按降序排序) (编辑:李大同) 【声明】本站内容均来自网络,其相关言论仅代表作者个人观点,不代表本站立场。若无意侵犯到您的权利,请及时与联系站长删除相关内容!  | 
                  
