为了优化我的代码,我正在尝试创建自己的Indexer
和我自己的FindEntry
函数版本 - 这样我就可以在{{1}中执行以下操作类似于:
Dictionary
这很有用,因为我的字典键是一个结构 - 但有时候我有哈希码而不是密钥。
我正在寻找从object IDictionary.this[int key] {
get {
int num = this.FindEntry(key);
if (num >= 0) {
return this.entries[num].value;
}
return null;
}
set {
Dictionary<TKey, TValue>.VerifyValueType(value);
this [key] = (TValue)((object)value);
}
}
private int FindEntry (int key) {
if (this.buckets != null) {
int num = key & 2147483647;
for (int i = this.buckets[num % this.buckets.Length]; i >= 0; i = this.entries[i].next) {
if (this.entries[i].hashCode == num && this.comparer.Equals(this.entries[i].key, key)) {
return i;
}
}
}
return -1;
}
重写以外的解决方案<{1}} - 但我怀疑这可能是唯一的方法,因为变量Dictionary<TKey, TValue>
在它内部是私人的。
以下是我的代码的基本示例,以帮助展示我正在尝试完成的任务。
System
和
entries
在上面的struct SuperKey : IEquatable<SuperKey> {
public int Id;
public int Environment;
public override int GetHashCode() {
return this.Id;
}
public override bool Equals(object other) {
return other is SuperKey ? Equals((SuperKey)other) : false;
}
public bool Equals(SuperKey other) {
return this.Id == other.Id && this.Environment == other.Environment;
}
}
方法中,请注意以下一行:
class Example { Dictionary<SuperKey, Player> players; void MyFunction() { SuperKey sk = new SuperKey(36, 1); Player p1 = new Player(); players.Add(sk, p1); } void ReceiveEventForPlayer(int id, PlayerEventName name) { ReceiveEventForPlayer(id, 0, name); } void ReceiveEventForPlayer(int id, int environment, PlayerEventName name) { Player p = players[new SuperKey(id, 1)]; } }
我更愿意使用:
ReceiveEventForPlayer
但是这不起作用......实际上 理想的是能够使用 语法。
答案 0 :(得分:1)
您对可能无效的Dictionary<TKey, TValue>
的实施做了很多假设。例如:
您还假设您可以访问基类的内部数据结构,这是不可能的。据我所知,buckets
类的受保护接口中没有Dictionary
数组。
从您发布的内容来看,似乎您保存的唯一执行时间(如果您的假设是正确的)将是计算每个项目的哈希码所花费的时间。通过在创建项目时(即在构造函数中)计算项目的哈希码并缓存它,可以轻松解决这个问题。那么,您的GetHashCode
方法只是return this.cachedHashCode;
当然,假设您放置在字典中的项目是不可变的。或者,至少,用于确定相等性的任何字段都是不可变的。
最后,您确定Dictionary
是您计划绩效的限制因素吗?如果没有,也许你的优化工作会更好地花在其他地方。
答案 1 :(得分:0)
Jim和Jon是正确的,我认为解决问题的方法很简单:
只需更改为GetHashCode
以连接db number,“ - ”和用户编号,然后在该字符串上调用基本GetHashCode。
通过这种方式,您无需在生产和调试中更改实现。