我正在寻找对 HashSet 设计师的见解。据我所知,我的问题适用于 Java 和 C# HashSet,这让我觉得一定有一些充分的理由,尽管我自己想不出任何理由。
当我将一个项目插入到 HashSet 中后,为什么不通过枚举就无法检索该项目,这几乎是一个高效的操作?特别是因为 HashSet 是以支持高效检索的方式显式构建的。
让 Remove(x) 和 Contains(x) 返回正在删除或包含的实际项目通常对我很有用。这不一定是我传递给Remove(x) 或Contains(x) 函数的项目。当然,我想我可以通过 HashMap 达到相同的效果,但是当完全可以用集合来做到这一点时,为什么要浪费所有空间和精力呢?
我可以理解,可能存在一些设计问题,即添加此功能将允许使用 HashSet,这与其在框架中的角色或未来角色不一致,但如果是这样,那么这些设计问题是什么?
Edit
为了回答更多问题,以下是更多详细信息:
我正在使用具有重写的哈希码、等于等的不可变引用类型来模拟 C# 中的值类型。假设该类型有成员 A、B 和 C。哈希码、等于等仅依赖于 A 和 B。给定一些 A 和 B,我希望能够从哈希集中检索等效项并得到它的 C。我不会'看来无法使用 HashSet 来实现这一点,但我至少想知道这是否有任何充分的理由。伪代码如下:
public sealed class X{
object A;
object B;
object extra;
public int HashCode(){
return A.hashCode() + B.hashCode();
}
public bool Equals(X obj){
return obj.A == A && obj.B == B;
}
}
hashset.insert(new X(1,2, extra1));
hashset.contains(new X(1,2)); //returns true, but I can't retrieve extra
在 .Net 中,您可能正在寻找的是 KeyedCollectionhttp://msdn.microsoft.com/en-us/library/ms132438.aspx http://msdn.microsoft.com/en-us/library/ms132438.aspx
您可以通过一些“通用”的聪明才智来避免每次重新实现这个抽象类的麻烦。 (参见 IKeyedObject`1。)
注意:任何实现 IKeyedObject`1 的数据传输对象都应该有一个重写的 GetHashCode 方法,只需返回 this.Key.GetHashCode();平等也同样如此......
我的基类库通常最终会包含这样的内容:
public class KeyedCollection<TItem> : System.Collections.ObjectModel.KeyedCollection<TItem, TItem>
where TItem : class
{
public KeyedCollection() : base()
{
}
public KeyedCollection(IEqualityComparer<TItem> comparer) : base(comparer)
{
}
protected override TItem GetKeyForItem(TItem item)
{
return item;
}
}
public class KeyedObjectCollection<TKey, TItem> : System.Collections.ObjectModel.KeyedCollection<TKey, TItem>
where TItem : class, IKeyedObject<TKey>
where TKey : struct
{
public KeyedCollection() : base()
{
}
protected override TItem GetKeyForItem(TItem item)
{
return item.Key;
}
}
///<summary>
/// I almost always implement this explicitly so the only
/// classes that have access without some rigmarole
/// are generic collections built to be aware that an object
/// is keyed.
///</summary>
public interface IKeyedObject<TKey>
{
TKey Key { get; }
}
本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)