简体   繁体   English

从列表中获取不同的值 <T> 在C#中

[英]Get Distinct values from List<T> in c#

Hi Programmers! 嗨,程序员! Actually i need the distinct values from the List after adding some values to List. 实际上,在将一些值添加到列表后,我需要列表中的不同值。 My code goes like this 我的代码是这样的

             List<Employee_Details> Temp = new List<Employee_Details>();
             Temp =(List<Employee_Details>) newform.Tag;
             EMP_DETAILS.Concat(Temp).Distinct();

But i directly ignore and do not add the values. 但是我直接忽略并且不添加值。

Please help me out. 请帮帮我。

Distinct prefers both GetHashCode and Equals to be defined either for the type being compared, or to have an equality comparer supplied. Distinct倾向于同时为要比较的类型定义GetHashCodeEquals或提供相等比较器。 If two objects have the same hash code, then they are checked for equality. 如果两个对象具有相同的哈希码,则将检查它们是否相等。

You can implement GetHashCode and Equals for your type - but I sometimes find that a definition of equality in one case isn't always suitable for all cases - ie in UI cases it might be enough only to check that two objects' IDs match, because the UI might not have all the same data defined on the object that is actually available (therefore a single true equality can't always be satisfied). 您可以为您的类型实现GetHashCodeEquals但是我有时会发现在一种情况下定义相等并不总是适用于所有情况-即在UI情况下,仅检查两个对象的ID是否匹配就足够了,因为UI可能没有在对象上定义的所有实际可用的相同数据(因此,不能始终满足单个真正的相等性)。

So I prefer to implement the IEqualityComparer<T> type for Employee_Details and then supply an instance of it to the Distinct method 因此,我更喜欢为Employee_Details实现IEqualityComparer<T>类型,然后将其实例提供给Distinct方法。

public class EmployeeDetailsComparer : IEqualityComparer<Employee_Details>
{
    #region IEqualityComparer<int> Members
    public bool Equals(Employee_Details x, Employee_Details y)
    {
        //define equality
      if(x == null)
      {
        return y == null;
      }
      else if(y == null) return false;
      //now check the fields that define equality - if it's a DB record,
      //most likely an ID field
      return x.ID == y.ID; //this is just A GUESS :)
    }

    public int GetHashCode(Employee_Details obj)
    {
        //define how to get a hashcode
        //most obvious would be to define it on the IDs, 
        //but if equality is defined across multiple fields
        //then one technique is to XOR (^) multiple hash codes together
        //null-check first
        if(obj == null) return 0;
        //now either:
        return obj.ID.GetHashCode();
        //or something like
        return obj.FirstName.GetHashCode() ^ obj.Surname.GetHashCode();
    }

    #endregion
}

Now you can do: 现在您可以执行以下操作:

EMP_DETAILS.Concat(Temp).Distinct(new EmployeeDetailsComparer());

Although note that doesn't actually do anything - you need to actually capture the return value of the Concat method, either as an IEnumerable<Employee_Details> , or 'realise' it into an array or list: 尽管注意实际上并没有做任何事情 -您实际上需要捕获 Concat方法的返回值(作为IEnumerable<Employee_Details>或“实现”到数组或列表中):

Employee_Details[] result = 
  EMP_DETAILS.Concat(Temp).Distinct(new EmployeeDetailsComparer()).ToArray();

Now you replace EMP_DETAILS with that. 现在,您将其替换为EMP_DETAILS If it's a List<Employee_Details> you can just do: 如果它是List<Employee_Details> ,则可以执行以下操作:

EMP_DETAILS = 
  EMP_DETAILS.Concat(Temp).Distinct(new EmployeeDetailsComparer()).ToList();

In reality implementing a good hashcode across multiple values is tricky - but the ^ approach works okay in most cases. 实际上,跨多个值实现良好的哈希码是很棘手的-但^方法在大多数情况下都可以。 The goal is to ensure that you get different hashcodes for different Employee_Details instances. 目的是确保您为不同的Employee_Details实例获得不同的哈希码。

Distinct method uses Equals comparison of contained objects. Distinct方法使用包含对象的Equals比较。 If you have default implementation of Equals in Employee_Details then you probably compare references. 如果您在Employee_Details具有Equals的默认实现,则您可能会比较引用。

So you have to options: 因此,您必须选择:

  1. Implement Equals method for your Employee_Details 为您的Employee_Details实现Equals方法
  2. Use overload of Distinct method that accepts IEqualityComparer 使用接受IEqualityComparer的Distinct方法的重载

You need to implement IEqualityComparer<T> in your class and provide your own GetHashCode and Equals methods. 您需要在您的类中实现IEqualityComparer<T> ,并提供自己的GetHashCodeEquals方法。

http://msdn.microsoft.com/en-us/library/ms132040.aspx http://msdn.microsoft.com/en-us/library/ms132040.aspx

class Employee_Details : IEqualityComparer
{
    public int Employee_ID;

    public Employee_Details(int empID)
    {
        Employee_ID = empID;
    }

    public new bool Equals(object x, object y)
    {
        return x.ToString().Equals(y.ToString());
    }

    public int GetHashCode(object obj)
    {
        return obj.ToString().ToLower().GetHashCode();
    }

    public override String ToString()
    {
        return Employee_ID.ToString();
    }
}

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM