2015-01-08 3 views
0

У меня следующий класс, который я использую, чтобы сравнить некоторые объекты, похоже, это:Равно Удалить неправильное назначение внутри Равно

Imports System.Collections.Generic 

Public Class Part 
    Implements IEqualityComparer(Of Part) 

    Public _comparisonType As EqualsComparmission 

    Public Sub New(ComparisonType As EqualsComparmission) 
     Me._comparisonType = ComparisonType 
    End Sub 

    Public Sub New() 
    End Sub 

    Public Property PartName() As String 
     Get 
      Return m_PartName 
     End Get 
     Set(value As String) 
      m_PartName = value 
     End Set 
    End Property 
    Private m_PartName As String 

    Public Property PartId() As Integer 
     Get 
      Return m_PartId 
     End Get 
     Set(value As Integer) 
      m_PartId = value 
     End Set 
    End Property 
    Private m_PartId As Integer 

    Public Overrides Function ToString() As String 
     Return "ID: " & PartId & " Name: " & PartName 
    End Function 


    Public Function Equals1(x As Part, y As Part) As Boolean Implements System.Collections.Generic.IEqualityComparer(Of Part).Equals 
     If x Is Nothing AndAlso y Is Nothing Then Return True 
     If x Is Nothing OrElse y Is Nothing Then Return False 

     Select Case _comparisonType 
      Case EqualsComparmission.PartId 
       Return x.PartId = y.PartId 
      Case EqualsComparmission.PartName 
       Return String.Equals(x.PartName, y.PartName) 
      Case EqualsComparmission.PartId_and_PartName 
       Return x.PartId = y.PartId AndAlso String.Equals(x.PartName, y.PartName) 
      Case Else 
       Throw New NotSupportedException("Unknown comparison type for parts: " & _comparisonType.ToString()) 
     End Select 
    End Function 

    Public Function GetHashCode1(obj As Part) As Integer Implements System.Collections.Generic.IEqualityComparer(Of Part).GetHashCode 
     Select Case _comparisonType 
      Case EqualsComparmission.PartId 
       Return obj.PartId 
      Case EqualsComparmission.PartName 
       Return If(obj.PartName Is Nothing, 0, obj.PartName.GetHashCode()) 
      Case EqualsComparmission.PartId_and_PartName 
       Dim hash = 17 

       hash = hash * 23 + obj.PartId 
       hash = hash * 23 + If(obj.PartName Is Nothing, 0, obj.PartName.GetHashCode()) 
       Return hash 
      Case Else 
       Throw New NotSupportedException("Unknown comparison type for parts: " & _comparisonType.ToString()) 
     End Select 
    End Function 

    Public Overrides Function Equals(obj As Object) As Boolean 
     If obj Is Nothing Then 
      Return False 
     End If 
     Dim objAsPart As Part = TryCast(obj, Part) 
     Dim result As Boolean = False 
     Select Case _comparisonType 
      Case EqualsComparmission.PartId 
       result = Me.PartId.Equals(objAsPart.PartId) 
      Case EqualsComparmission.PartName 
       result = Me.PartName.Equals(objAsPart.PartName) 
      Case EqualsComparmission.PartId_and_PartName 
       result = Me.PartId.Equals(objAsPart.PartId) And Me.PartName.Equals(objAsPart.PartName) 
      Case Else 
       Throw New NotSupportedException("Unknown comparison type for parts: " & _comparisonType.ToString()) 
     End Select 

     Return result 
    End Function 

End Class 


Public Enum EqualsComparmission 

    PartId 
    PartName 
    PartId_and_PartName 

End Enum 

Я могу правильно сравнить Сравнить например:

Console.WriteLine("Was it found: " & parts.Contains(New Part() With { _ 
     .PartId = 1634, _ 
     .PartName = "shift lever" _ 
    }, New Part(EqualsComparmission.PartId_and_PartName))) 

но У меня проблема с Remove, метод всегда будет равен первому значению перечисления PartId, независимо от того, что я посылаю конструктору, почему?

Dim deleted As Boolean = parts.Remove(New Part(EqualsComparmission.PartId_and_PartName) With { 
      .PartId = 11, _ 
      .PartName = "al7a" _ 
     }) 
+0

В стороне: вам не нужно писать то же самое дважды. 'Equals (object)' может вызывать 'Equals1' после успешного выполнения объекта' Part'. Тогда вам нужно только поддерживать одно место. Однако основной причиной предоставления «IEqualityComparer» является то, что он может быть не связан с классом, который он сравнивает. Реализация как в 'Part' является избыточной. –

+0

i удален полностью Равный метод и удаленный объект IEquatable (Of Part) из моего класса, но после этого при использовании Dim deleted As Boolean = parts.Remove (Новая часть (EqualsComparmission.PartId_and_PartName) С {_ .PartId = 11, _ .PartName = "something" _ }), он всегда дает ложные данные и во время отладки никогда не обогащает метод Equals1. – unknown

+0

, где я делаю ошибку? У меня теперь только Equals1 – unknown

ответ

1

Предполагая, что parts является List(Of Part), вы можете упростить удаление (и проверки) с помощью LINQ:

'check it exists 
Debug.WriteLine("Was it found: " & parts.Exists(Function(x) x.PartId = 1634 And x.PartName = "shift lever")) 

'Remove by PartId and PartName 
Dim deleted As Integer = parts.RemoveAll(Function(x) x.PartId = 1634 And x.PartName = "shift lever") 
'or just by PartId 
Dim deleted As Integer = parts.RemoveAll(Function(x) x.PartId = 1634) 
'or just by PartName 
Dim deleted As Integer = parts.RemoveAll(Function(x) x.PartName = "shift lever") 

Вы можете просто указать, если вы хотите удалить части, где PartId матчи или PartName соответствует или оба. Таким образом, вы можете избавиться от Equals и Enums

+0

Я знаю, что могу сделать свой путь, но мне интересно, почему, когда я делаю Remove, как показано, он всегда идет в Equas select case - всегда сначала перечисляет, независимо от того, что я посылаю конструктору, его множества всегда PartId. – unknown

+0

Я сделал расследование после того, как конструктор попал, а enum установлен в свойство правильно, но когда он переходит к свойству Equl, изменив значение на значение enum по умолчанию. Что происходит?? – unknown

 Смежные вопросы

  • Нет связанных вопросов^_^