C# 创建自定义泛型集合

C# 创建自定义泛型集合,c#,collections,C#,Collections,我想创建一个自定义的通用集合,如果元素少于10个,它将存储在列表中;如果元素较多,则存储在分类列表中 我为SortedList实现了ICollection(KeyValuePair),为List实现了ICollection,但我不知道接下来该怎么做。请有人给我一个提示,如果元素少于10个,应该如何实现“将元素存储在列表中”,如果元素较多,应该如何实现“将元素存储在分类列表中” class CustomCollection<T, V> : ICollection<KeyValue

我想创建一个自定义的通用集合,如果元素少于10个,它将存储在
列表
中;如果元素较多,则存储在
分类列表

我为
SortedList
实现了
ICollection(KeyValuePair)
,为
List
实现了
ICollection
,但我不知道接下来该怎么做。请有人给我一个提示,如果元素少于10个,应该如何实现“将元素存储在
列表中”
,如果元素较多,应该如何实现“将元素存储在
分类列表中”

class CustomCollection<T, V> : ICollection<KeyValuePair<T, V>>, ICollection<T>
    {
        private readonly ICollection<T> _list = new List<T>();
        private readonly ICollection<KeyValuePair<T, V>> _sortlist = new SortedList<T, V>();

        public void Add(KeyValuePair<T, V> item)
        {
            _sortlist.Add(item);
        }

        public void Add(T item)
        {
            _list.Add(item);
        }
    }
类CustomCollection:ICollection,ICollection
{
私有只读ICollection_list=new list();
私有只读ICollection_sortlist=new SortedList();
公共作废添加(KeyValuePair项)
{
_分类表添加(项目);
}
公共作废新增(T项)
{
_列表。添加(项目);
}
}

这里是完整的实现。它相当长,完全未经测试:-)您可以从调试中获得乐趣

有一些有趣的地方:两个比较器的使用(不是一个好主意),如何处理
null
(它抛出
null引用异常
,如SortedList),以及在各种
添加
删除
清除
集合之间的切换。请注意,通常
SortedList
“隐藏”所有直接处理
KeyValuePair
的方法。我选择了做同样的事情。其他注意事项:要在
列表中“搜索”,我将进行线性搜索。更聪明(更快)的方法是执行
列表.BinarySearch

public class CustomCollection<TKey, TValue> : IDictionary<TKey, TValue>
{
    protected List<KeyValuePair<TKey, TValue>> List { get; set; }
    protected SortedList<TKey, TValue> SortedList { get; set; }

    // Two comparers needed: an EqualityComparer and a Comparer to sort
    // We could simply use the Comparer and compare the result to 0
    // instead of using an EqualityComparer and a Comparer
    protected readonly EqualityComparer<TKey> EqualityComparer = EqualityComparer<TKey>.Default;
    protected readonly Comparer<TKey> Comparer = Comparer<TKey>.Default;

    public int MaxCapacityList { get; protected set; }

    public CustomCollection(int maxCapacityList = 10)
    {
        MaxCapacityList = maxCapacityList;

        if (maxCapacityList > 0)
        {
            List = new List<KeyValuePair<TKey, TValue>>();
        }
        else
        {
            SortedList = new SortedList<TKey, TValue>();
        }
    }

    public bool IsUsingList
    {
        get
        {
            return List != null;
        }
    }

    public void Add(TKey key, TValue value)
    {
        if (IsUsingList)
        {
            if (key == null)
            {
                throw new ArgumentNullException();
            }

            if (List.Any(x => EqualityComparer.Equals(x.Key, key)))
            {
                throw new ArgumentException();
            }
        }

        if (IsUsingList && List.Count < MaxCapacityList)
        {
            List.Add(new KeyValuePair<TKey, TValue>(key, value));

            // Only place we need to sort. Only "real" Add method
            List.Sort((x, y) => Comparer.Compare(x.Key, y.Key));
        }
        else
        {
            if (IsUsingList && List.Count == MaxCapacityList)
            {
                SortedList = new SortedList<TKey, TValue>();

                foreach (var kv in List)
                {
                    SortedList.Add(kv.Key, kv.Value);
                }

                List = null;
            }

            SortedList.Add(key, value);
        }
    }

    public bool ContainsKey(TKey key)
    {
        if (IsUsingList)
        {
            if (key == null)
            {
                throw new ArgumentNullException();
            }

            if (List.Any(x => EqualityComparer.Equals(x.Key, key)))
            {
                return true;
            }

            return false;
        }

        return SortedList.ContainsKey(key);
    }

    public ICollection<TKey> Keys
    {
        get
        {
            if (IsUsingList)
            {
                return List.ConvertAll(x => x.Key);
            }

            return SortedList.Keys;
        }
    }

    public bool Remove(TKey key)
    {
        if (IsUsingList)
        {
            if (key == null)
            {
                throw new ArgumentNullException();
            }

            for (int ix = 0; ix < List.Count; ix++)
            {
                if (EqualityComparer.Equals(List[ix].Key, key))
                {
                    List.RemoveAt(ix);
                    return true;
                }
            }

            return false;
        }

        bool result = SortedList.Remove(key);

        if (result && SortedList.Count == MaxCapacityList && MaxCapacityList > 0)
        {
            List = new List<KeyValuePair<TKey, TValue>>();

            foreach (var kv in SortedList)
            {
                List.Add(new KeyValuePair<TKey, TValue>(kv.Key, kv.Value));
            }

            SortedList = null;
        }

        return result;
    }

    public bool TryGetValue(TKey key, out TValue value)
    {
        if (IsUsingList)
        {
            if (key == null)
            {
                throw new ArgumentNullException();
            }

            for (int i = 0; i < List.Count; i++)
            {
                if (EqualityComparer.Equals(List[i].Key, key))
                {
                    value = List[i].Value;
                    return true;
                }
            }

            value = default(TValue);
            return false;
        }

        return SortedList.TryGetValue(key, out value);
    }

    public ICollection<TValue> Values
    {
        get
        {
            if (IsUsingList)
            {
                return List.ConvertAll(x => x.Value);
            }

            return SortedList.Values;
        }
    }

    public TValue this[TKey key]
    {
        get
        {
            if (IsUsingList)
            {
                if (key == null)
                {
                    throw new ArgumentNullException();
                }

                for (int ix = 0; ix < List.Count; ix++)
                {
                    if (EqualityComparer.Equals(List[ix].Key, key))
                    {
                        return List[ix].Value;
                    }
                }

                throw new KeyNotFoundException();
            }

            return SortedList[key];
        }
        set
        {
            if (IsUsingList)
            {
                if (key == null)
                {
                    throw new ArgumentNullException();
                }

                for (int ix = 0; ix < List.Count; ix++)
                {
                    if (EqualityComparer.Equals(List[ix].Key, key))
                    {
                        List[ix] = new KeyValuePair<TKey, TValue>(key, value);
                        return;
                    }
                }

                Add(key, value);

                return;
            }

            SortedList[key] = value;
        }
    }

    void ICollection<KeyValuePair<TKey, TValue>>.Add(KeyValuePair<TKey, TValue> item)
    {
        Add(item.Key, item.Value);
    }

    public void Clear()
    {
        if (IsUsingList)
        {
            List.Clear();
        }
        else
        {
            if (MaxCapacityList > 0)
            {
                List = new List<KeyValuePair<TKey, TValue>>();
                SortedList = null;
            }
            else
            {
                SortedList.Clear();
            }
        }
    }

    bool ICollection<KeyValuePair<TKey, TValue>>.Contains(KeyValuePair<TKey, TValue> item)
    {
        if (IsUsingList)
        {
            if (item.Key == null)
            {
                throw new ArgumentNullException();
            }

            return List.Any(x => EqualityComparer.Equals(x.Key, item.Key));
        }

        return ((ICollection<KeyValuePair<TKey, TValue>>)SortedList).Contains(item);
    }

    void ICollection<KeyValuePair<TKey, TValue>>.CopyTo(KeyValuePair<TKey, TValue>[] array, int arrayIndex)
    {
        if (IsUsingList)
        {
            List.CopyTo(array, arrayIndex);
            return;
        }

        ((ICollection<KeyValuePair<TKey, TValue>>)SortedList).CopyTo(array, arrayIndex);
    }

    public int Count
    {
        get { return IsUsingList ? List.Count : SortedList.Count; }
    }

    public bool IsReadOnly
    {
        get { return false; }
    }

    bool ICollection<KeyValuePair<TKey, TValue>>.Remove(KeyValuePair<TKey, TValue> item)
    {
        if (IsUsingList)
        {
            if (item.Key == null)
            {
                throw new ArgumentNullException();
            }

            for (int ix = 0; ix < List.Count; ix++)
            {
                if (EqualityComparer.Equals(List[ix].Key, item.Key))
                {
                    var comparer2 = EqualityComparer<TValue>.Default;

                    if (comparer2.Equals(List[ix].Value, item.Value))
                    {
                        List.RemoveAt(ix);
                        return true;
                    }

                    return false;
                }
            }

            return false;
        }

        bool result = ((ICollection<KeyValuePair<TKey, TValue>>)SortedList).Remove(item);

        if (result && SortedList.Count == MaxCapacityList && MaxCapacityList > 0)
        {
            List = new List<KeyValuePair<TKey, TValue>>();

            foreach (var kv in SortedList)
            {
                List.Add(new KeyValuePair<TKey, TValue>(kv.Key, kv.Value));
            }

            SortedList = null;
        }

        return result;
    }

    public IEnumerator<KeyValuePair<TKey, TValue>> GetEnumerator()
    {
        return IsUsingList ? List.GetEnumerator() : SortedList.GetEnumerator();
    }

    IEnumerator IEnumerable.GetEnumerator()
    {
        // Chained to the other GetEnumerator()
        return GetEnumerator();
    }
}
公共类CustomCollection:IDictionary
{
受保护列表{get;set;}
受保护的分类列表分类列表{get;set;}
//需要两个比较器:一个EqualityComparer和一个用于排序的比较器
//我们可以简单地使用比较器并将结果与0进行比较
//而不是使用EqualityComparer和比较器
受保护的只读EqualityComparer EqualityComparer=EqualityComparer.Default;
受保护的只读比较器Comparer=Comparer.Default;
public int MaxCapacityList{get;protected set;}
公共CustomCollection(int maxCapacityList=10)
{
MaxCapacityList=MaxCapacityList;
如果(maxCapacityList>0)
{
列表=新列表();
}
其他的
{
SortedList=新的SortedList();
}
}
公共图书馆正在使用列表
{
得到
{
返回列表!=null;
}
}
公共无效添加(TKey键,TValue值)
{
如果(正在使用列表)
{
if(key==null)
{
抛出新ArgumentNullException();
}
if(List.Any(x=>EqualityComparer.Equals(x.Key,Key)))
{
抛出新ArgumentException();
}
}
if(使用列表和列表计数Comparer.Compare(x.Key,y.Key));
}
其他的
{
if(IsUsingList&&List.Count==MaxCapacityList)
{
SortedList=新的SortedList();
foreach(列表中的var kv)
{
分类列表。添加(千伏键,千伏值);
}
列表=空;
}
SortedList.Add(键、值);
}
}
公共bool ContainsKey(TKey)
{
如果(正在使用列表)
{
if(key==null)
{
抛出新ArgumentNullException();
}
if(List.Any(x=>EqualityComparer.Equals(x.Key,Key)))
{
返回true;
}
返回false;
}
返回分拣列表。集装箱箱(钥匙);
}
公共ICollection密钥
{
得到
{
如果(正在使用列表)
{
返回List.ConvertAll(x=>x.Key);
}
返回分类列表。键;
}
}
公用门移除(TKey)
{
如果(正在使用列表)
{
if(key==null)
{
抛出新ArgumentNullException();
}
for(intix=0;ix0)
{
列表=新列表();
foreach(分类列表中的var kv)
{
添加(新的KeyValuePair(千伏键,千伏值));
}
SortedList=null;
}
返回结果;
}
公共bool TryGetValue(TKey键,out TValue值)
{
如果(正在使用列表)
{
if(key==null)
{
抛出新ArgumentNullException();
}
for(int i=0;ix.Value);
}
返回分类列表值;
}
}
公共TValue此[TKey]
{
得到
{
如果(正在使用列表)
{