我有一个键和值列表,我希望通过自定义Comparer(Of T)
按键排序。
我尝试使用SortedDictionary
,但一直得到不正确的结果,因为它使用比较器来查看项目是否相同。例如,调用SortedDictionary.ContainsKey()
将返回false,即使它确实包含密钥。
当我在调用ContainsKey()
后逐步执行代码时,它将转到comparer.Compare(x, y)
函数。然后它只会与dicionary中的一些键进行比较,并以某种方式跳过匹配的项目(我确保确实存在)。我认为这是某种优化,根据comparer.Compare()
函数返回的内容跳过某些项目?
是否可以使用仅使用比较器进行排序的字典? 或者有什么想法可以克服这个问题?
非常感谢!
编辑:我正在使用Type
对象作为字典的密钥
编辑:比较器代码:(游戏引擎的渲染器根据其DrawOrder属性进行排序(如果有的话))
Public Class RendererComparer
Inherits Comparer(Of Type)
Public Overrides Function Compare(ByVal x As Type, ByVal y As Type) As Integer
If x Is y Then Return 0
If x Is Nothing Then
Return -1
Else
Dim draworderx As Integer = GetDrawOrder(x)
Dim drawordery As Integer = GetDrawOrder(y)
If draworderx < drawordery Then
Return -1
Else
Return 1
End If
End If
End Function
Private Function GetDrawOrder(ByVal t As Type) As Integer
Dim p As PropertyInfo = t.GetProperty("DrawOrder")
If p Is Nothing Then Return 0
Dim o As Object = p.GetValue(Nothing, Nothing)
Return CInt(o)
End Function
End Class
答案 0 :(得分:1)
如果你有两个不同的项目使用相同的GetDrawOrder,那么你违反了比较器的合同。因此,排序可能会中断并导致未定义的行为。
特别是你违反了比较(a,b)== - 比较(b,a)
答案 1 :(得分:1)
您对GetDrawOrder的实现很可疑。你希望在类上获得静态属性然后获得它的价值吗?如果是这样,当您获得BindingFlags.Static
时,您应该使用PropertyInfo
。
如果要向某个类型添加属性,则添加自定义属性会更加清晰。
e.g。
[DrawOrder(5)]
public class MyType { ...}
然后,只需询问OfType
DrawOrder类型的属性来获取整数绘制顺序值,并通过比较它们返回结果。
答案 2 :(得分:0)
听起来您可能需要覆盖GetHashcode()
以将匹配值散列到相同的散列键上。在比较完全匹配的值之前,字典类通常在进行相等性测试之前使用哈希码。