具有可选键的多键字典
本文关键字:字典 | 更新日期: 2023-09-27 18:06:37
我需要一个具有2种不同类型的多个键的字典(int和string,都是唯一的,因此它们只能出现在1个键中)。下面是一个示例:组信息(GroupInfo)可以通过GroupdId或其中一个成员名查询:
GroupId MemberNames GroupInfo
{1, John, Mary, Joe} ==> {GroupInfo}
因此,当id(1)或其中一个成员名(John)请求时,应该返回组信息。
我的第一个解决方案是创建一个键,该键使用覆盖的Equals方法包装GroupdId和MemberNames,该方法比较groupid并查找成员列表。但是,要使这些条目相等:
GroupId MemberNames
{0, John}
{1, null}
{1, Mary}
GetHashCode必须返回相同的const值。这将导致字典变成链表,并且在最佳情况下性能下降到查找O(N)次。
另一个解决方案是分别保存2个字典:GroupId ==> GroupInfo, MemberName ==> GroupInfo。
还有其他想法吗?
根据你在评论中的描述
你怎么按键删除的?例如,给定一个键"John",所有其他键也应该被删除。
现在你可能已经很清楚,一本"字典"并不是你想要的。主要是因为您需要多种键类型,并且需要将键映射到其他键。
所以你可以创建你自己的类来实现字典。基本如下:
class MultiKeyDictionary : IDictionary
{
Dictionary<string, GroupInfo> stringDict = new Dictionary<string, GroupInfo>();
Dictionary<int, GroupInfo> intDict = new Dictionary<int, GroupInfo>();
Dictionary<GroupInfo, List<object>> keysDict = new Dictionary<GroupInfo, List<object>>();
//Each of these would add to their own dictionary, as well as adding the backwards
//entry in the "keysDict"
public void Add(string memberName, GroupInfo value);
public void Add(int key, GroupInfo value);
public bool Contains(string key);
public bool Contains(int key);
//This would be the enumerator of the "keys" of "keysDict"
//because it is actually a list of all GroupInfos
public IDictionaryEnumerator GetEnumerator()
public ICollection NameKeys;
public ICollection GroupIDKeys;
//This is to adhere to the interface. It should be carefully commented or even deprecated.
public ICollection Keys;
//For this, you look up the GroupInfo for the key, then do
//foreach(object key in keysDict[<groupInfoIJustLookedUp>]) {
// if(key.gettype == typeof(string) stringDict.Remove(key);
// else if (key.gettype == typeof(int) intDict.Remove(key);
// else //WHAT?!?
//}
public void Remove(string key);
public void Remove(int key);
//This would be the "Keys" collection of the "keysDict"
public ICollection Values;
//etc... etc...
public object this[string memberName];
public object this[int groupId];
}
为了只维护一个字典,考虑将GroupId (int)转换为字符串并将其用作键(数字'键'不应与名称键冲突)。维护对键的引用,这样如果一个键被删除,其余的键也会被删除。