Quando usar IComparable Vs. IComparer
-
22-08-2019 - |
Pergunta
Eu estou tentando descobrir qual dessas interfaces Eu preciso implementar. Ambos, essencialmente, fazer a mesma coisa. Quando devo usar um sobre o outro?
Solução
Bem, eles não são muito a mesma coisa que IComparer<T>
é implementado em um tipo que é capaz de comparar dois objetos diferentes enquanto IComparable<T>
é implementado em tipos que são capazes de se comparar com outras instâncias do mesmo tipo.
I tendem a usar IComparable<T>
para momentos em que eu preciso saber como outra instância se refere a instância this
. IComparer<T>
é útil para classificar coleções como a IComparer<T>
está fora da comparação.
Outras dicas
Use IComparable<T>
quando a classe tem uma relação intrínseca.
Use IComparer<T>
quando você quer um método de comparação que não seja a classe comparação intrínseca, se ele tiver um.
Depende da entidade. Por exemplo a seguir para uma classe como "Student", ele vai fazer sentido ter IComparable com base no nome.
class Student : IComparable
{
public string Name { get; set; }
public int MathScore { get; set; }
public int EnglishScore { get; set; }
public int TotalScore
{
get
{
return this.MathScore + this.EnglishScore;
}
}
public int CompareTo(object obj)
{
return CompareTo(obj as Student);
}
public int CompareTo(Student other)
{
if (other == null)
{
return 1;
}
return this.Name.CompareTo(other.Name);
}
}
Mas se um professor 'A' quer comparar alunos com base em MathScore e professor 'B' quer comparar alunos com base em EnglishScore. Será boa ideia para implementar IComparer separadamente. (Mais como um padrão de estratégia)
class CompareByMathScore : IComparer<Student>
{
public int Compare(Student x, Student y)
{
if (x.MathScore > y.MathScore)
return 1;
if (x.MathScore < y.MathScore)
return -1;
else
return 0;
}
}
Tudo depende se o seu tipo é mutável ou não. Você deve única implementar IComparable em tipos não-mutáveis. Note que se você implementar IComparable, você deve substituir Equals, juntamente com os ==,! =,
Citando Dave G de este blog :
Mas a resposta correta é a implementação de IComparer em vez de IComparable se os objetos são mutáveis, e passar uma instância da IComparer para funções de ordenação quando necessário.
Uma vez que o IComparer é apenas um objeto descartável usado na triagem naquele ponto no tempo, o objeto pode ter qualquer semântica mutáveis ??que você deseja. Além disso, ele não exige ou mesmo sugerir o uso de Equals, GetHashCode ou == -. Você é livre para defini-lo de qualquer maneira, por favor
Finalmente, você pode definir vários de IComparer para o seu tipo de triagem em diferentes campos ou com regras diferentes. Isso é muito mais flexível do que ser preso com uma definição.
Em resumo:. Use IComparable para tipos de valor e IComparer para tipos de referência
explicação simples através de uma história
High school basquete. É uma escolha pátio da escola para as equipes. Eu quero começar o mais alto / melhores pessoas / mais rápido no meu time. O que eu faço?
IComparer interface - Compare duas pessoas separar as pessoas
- Isso me permite comparar dois rapazes alinhados ......... é basicamente isso. Fred vs John .......... i jogá-los em uma classe concreta que implementa a interface.
Compare(Fred, John)
e ele cospe quem é melhor.
E sobre IComparable -? Compare-se com outra pessoa
Você esteve no FB recentemente? Você vê outras pessoas fazendo coisas legais:. Viajando o mundo, criando invenções, enquanto eu estou fazendo algo não tão cool - bem o que estamos fazendo é fazendo uso da interface IComparable
- Estamos comparando a instância atual (você mesmo) com outro objeto (alguém), que é do mesmo tipo (pessoa).
E sobre a classe Comparer?
A classe Comparer é uma classe base abstrata que implementa a interface IComparer. Você deve derivar dessa classe para ter uma implementação concreta. de qualquer maneira, a Microsoft recomenda que você use a classe Comparer ao invés de implementar a interface IComparer:
Recomendamos que você derivar da classe Comparer em vez de implementar a interface IComparer, porque a classe Comparer fornece uma implementação de interface explícita do método IComparer.Compare ea propriedade padrão que recebe o comparador padrão para o objeto.
Resumo
- IComparer -. Linha-se duas coisas e compará
- IComparable - se comparar com os outros sobre FB .
A esperança as histórias ajudá-lo a se lembrar.
Como já foi dito, eles não fazem a mesma coisa.
Em qualquer caso, esses dias eu não tendem a usar IComparer. Por que eu deveria? A sua responsabilidade (uma entidade externa usada para comparar dois objetos) pode ser tratado muito mais limpo com uma expressão lambda, semelhante à forma como a maioria dos métodos de trabalho do LINQ. Escrever uma lambda rápida que leva os objetos para comparar como argumentos e retorna um bool. E se o objeto define a sua própria operação de comparação intrínseca, pode implementar IComparable vez.
IComparable diz um objeto pode ser comparada com outra. IComparer é um objeto que pode comparar dois itens.
IComparer é uma interface que é usado para classificar a matriz, esta interface irá forçar a classe para implementar o Comparar (t x, y t), o qual irá comparar os dois objectos. A instância da classe que implementou essa interface é usada na classificação da matriz.
IComparable é uma interface é implementado no tipo que precisa para comparar os dois objetos do mesmo tipo, Esta interface comparável forçará a classe para implementar o seguinte método CompareTo (T obj)
IEqualityComparer é uma interface que é usado para localizar o objeto se é igual ou não, Agora vamos ver isso em uma amostra onde temos que encontrar o distinto de um objeto em uma coleção. Esta interface irá implementar um método Equals (T obj1, T obj2)
Agora vamos tomar um exemplo que temos uma classe Employee, com base nessa classe nós temos que criar uma coleção. Agora temos os seguintes requisitos.
classificar a matriz usando classe Array 2. Precisa de uma coleção usando Linq: Retire o Duplicar, Ordenar por superior para inferior, remova um ID de empregado
abstract public class Person
{
public string FirstName { get; set; }
public string LastName { get; set; }
public string Address { set; get; }
}
public enum SortType
{
ByID,
BySalary
}
EmployeeIdSorter classe pública: IComparer
{
int público Compare (Employee x, y Employee)
{
if (x.Id
public class EmployeeSalarySorter : IComparer<Employee>
{
public int Compare(Employee x, Employee y)
{
if (x.Salary < y.Salary)
return 1;
else if (x.Salary > y.Salary)
return -1;
else
return 0;
}
}
Para mais informações REFERÊ abaixo http://dotnetvisio.blogspot.in/2015/12 /usage-of-icomparer-icomparable-and.html