Lezen in het Engels

Delen via


IComparable De en IComparer interfaces gebruiken in Visual CSharp

In dit artikel wordt het gebruik van IComparer en IComparable interfaces in Visual C# beschreven.

Oorspronkelijke productversie: Visual C#
Oorspronkelijk KB-nummer: 320727

Samenvatting

De IComparable en IComparer interfaces worden om twee redenen in hetzelfde artikel besproken. Deze interfaces worden vaak samen gebruikt. Hoewel de interfaces vergelijkbaar zijn en vergelijkbare namen hebben, dienen ze verschillende doeleinden.

Als u een matrix hebt van typen (zoals tekenreeks of geheel getal) die al worden ondersteund IComparer, kunt u die matrix sorteren zonder expliciete verwijzing naar IComparer. In dat geval worden de elementen van de matrix gecast naar de standaard implementatie van IComparer (Comparer.Default) voor u. Als u echter sorteer- of vergelijkingsmogelijkheden wilt bieden voor uw aangepaste objecten, moet u een of beide interfaces implementeren.

In dit artikel wordt verwezen naar de Naamruimte System.Collectionsvan de Microsoft .NET Framework-klassebibliotheek.

IComparable

De rol van IComparable is om een methode te bieden voor het vergelijken van twee objecten van een bepaald type. Het is nodig als u een bestelmogelijkheid voor uw object wilt bieden. IComparable U kunt een standaardsorteervolgorde instellen voor uw objecten. Als u bijvoorbeeld een matrix met objecten van uw type hebt en u de Sort methode voor die matrix aanroept, IComparable geeft u de vergelijking van objecten tijdens het sorteren. Wanneer u de IComparable interface implementeert, moet u de CompareTo methode als volgt implementeren:

// Implement IComparable CompareTo method - provide default sort order.
int IComparable.CompareTo(object obj)
{
   Car c=(Car)obj;
   return String.Compare(this.make,c.make);
}

De vergelijking in de methode verschilt, afhankelijk van het gegevenstype van de waarde die wordt vergeleken. String.Compare wordt in dit voorbeeld gebruikt omdat de eigenschap die is gekozen voor de vergelijking een tekenreeks is.

IComparer

De rol van IComparer is om meer vergelijkingsmechanismen te bieden. U kunt bijvoorbeeld de volgorde van uw klasse opgeven voor verschillende velden of eigenschappen, oplopende en aflopende volgorde in hetzelfde veld, of beide.

Het gebruik IComparer is een proces in twee stappen. Declareer eerst een klasse die implementeert ICompareren implementeer vervolgens de Compare methode:

private class SortYearAscendingHelper : IComparer
{
   int IComparer.Compare(object a, object b)
   {
      Car c1=(Car)a;
      Car c2=(Car)b;
      if (c1.year > c2.year)
         return 1;
      if (c1.year < c2.year)
         return -1;
      else
         return 0;
   }
}

Notitie

Voor de IComparer.Compare methode is een tertiaire vergelijking vereist. 1, 0 of -1 wordt geretourneerd, afhankelijk van of de ene waarde groter is dan, gelijk aan of kleiner is dan de andere. De sorteervolgorde (oplopend of aflopend) kan worden gewijzigd door de logische operatoren in deze methode te wijzigen.

De tweede stap is het declareren van een methode die een exemplaar van uw IComparer object retourneert:

public static IComparer SortYearAscending()
{
   return (IComparer) new SortYearAscendingHelper();
}

In dit voorbeeld wordt het object gebruikt als het tweede argument wanneer u de overbelaste Array.Sort methode aanroept IComparerdie accepteert. Het gebruik van IComparer is niet beperkt tot matrices. Het wordt geaccepteerd als een argument in veel verschillende verzamelings- en besturingsklassen.

Stapsgewijs voorbeeld

In het volgende voorbeeld ziet u het gebruik van deze interfaces. Om te demonstreren IComparer en IComparablewordt er een klasse met de naam Car gemaakt. Het Car object heeft de eigenschappen make en year. Een oplopende sortering voor het veld Make wordt ingeschakeld via de IComparable interface en een aflopende sortering op het veld Make wordt ingeschakeld via de IComparer interface. Zowel oplopende als aflopende sorteringen worden geleverd voor de jaareigenschap met behulp van IComparer.

  1. Maak in Visual C# een nieuw consoletoepassingsproject. Noem de toepassing ConsoleEnum.

  2. Wijzig de naam van Program.cs als Host.cs en vervang de code door de volgende code.

    using System;
    
    namespace ConsoleEnum
    {
        class host
        {
           [STAThread]
           static void Main(string[] args)
           {
              // Create an array of Car objects.
              Car[] arrayOfCars= new Car[6]
              {
                 new Car("Ford",1992),
                 new Car("Fiat",1988),
                 new Car("Buick",1932),
                 new Car("Ford",1932),
                 new Car("Dodge",1999),
                 new Car("Honda",1977)
              };
    
              // Write out a header for the output.
              Console.WriteLine("Array - Unsorted\n");
    
              foreach(Car c in arrayOfCars)
                 Console.WriteLine(c.Make + "\t\t" + c.Year);
    
              // Demo IComparable by sorting array with "default" sort order.
              Array.Sort(arrayOfCars);
              Console.WriteLine("\nArray - Sorted by Make (Ascending - IComparable)\n");
    
              foreach(Car c in arrayOfCars)
                 Console.WriteLine(c.Make + "\t\t" + c.Year);
    
              // Demo ascending sort of numeric value with IComparer.
              Array.Sort(arrayOfCars,Car.SortYearAscending());
              Console.WriteLine("\nArray - Sorted by Year (Ascending - IComparer)\n");
    
              foreach(Car c in arrayOfCars)
                 Console.WriteLine(c.Make + "\t\t" + c.Year);
    
              // Demo descending sort of string value with IComparer.
              Array.Sort(arrayOfCars,Car.SortMakeDescending());
              Console.WriteLine("\nArray - Sorted by Make (Descending - IComparer)\n");
    
              foreach(Car c in arrayOfCars)
                 Console.WriteLine(c.Make + "\t\t" + c.Year);
    
              // Demo descending sort of numeric value using IComparer.
              Array.Sort(arrayOfCars,Car.SortYearDescending());
              Console.WriteLine("\nArray - Sorted by Year (Descending - IComparer)\n");
    
              foreach(Car c in arrayOfCars)
                 Console.WriteLine(c.Make + "\t\t" + c.Year);
    
              Console.ReadLine();
           }
       }
    }
    
  3. Voeg een klasse toe aan het project. Geef de klasse auto een naam.

  4. Vervang de code in Car.cs door de volgende code:

    using System;
    using System.Collections;
    namespace ConsoleEnum
    {
       public class Car : IComparable
       {
          // Beginning of nested classes.
          // Nested class to do ascending sort on year property.
          private class SortYearAscendingHelper: IComparer
          {
             int IComparer.Compare(object a, object b)
             {
                Car c1=(Car)a;
                Car c2=(Car)b;
    
                if (c1.year > c2.year)
                   return 1;
    
                if (c1.year < c2.year)
                   return -1;
    
                else
                   return 0;
             }
          }
    
          // Nested class to do descending sort on year property.
          private class SortYearDescendingHelper: IComparer
          {
             int IComparer.Compare(object a, object b)
             {
                Car c1=(Car)a;
                Car c2=(Car)b;
    
                if (c1.year < c2.year)
                   return 1;
    
                if (c1.year > c2.year)
                   return -1;
    
                else
                   return 0;
             }
          }
    
          // Nested class to do descending sort on make property.
          private class SortMakeDescendingHelper: IComparer
          {
             int IComparer.Compare(object a, object b)
             {
                Car c1=(Car)a;
                Car c2=(Car)b;
                 return String.Compare(c2.make,c1.make);
             }
          }
          // End of nested classes.
          private int year;
          private string make;
    
          public Car(string Make,int Year)
          {
             make=Make;
             year=Year;
          }
    
          public int Year
          {
             get  {return year;}
             set {year=value;}
          }
    
          public string Make
          {
             get {return make;}
             set {make=value;}
          }
          // Implement IComparable CompareTo to provide default sort order.
          int IComparable.CompareTo(object obj)
          {
             Car c=(Car)obj;
             return String.Compare(this.make,c.make);
          }
          // Method to return IComparer object for sort helper.
          public static IComparer SortYearAscending()
          {
             return (IComparer) new SortYearAscendingHelper();
          }
          // Method to return IComparer object for sort helper.
          public static IComparer SortYearDescending()
          {
             return (IComparer) new SortYearDescendingHelper();
          }
          // Method to return IComparer object for sort helper.
          public static IComparer SortMakeDescending()
          {
            return (IComparer) new SortMakeDescendingHelper();
          }
    
       }
    }
    
  5. Voer het project uit. De volgende uitvoer wordt weergegeven in het consolevenster :

    Array - Unsorted
    
    Ford 1992
    Fiat 1988
    Buick 1932
    Ford 1932
    Dodge 1999
    Honda 1977
    
    Array - Sorted by Make (Ascending - IComparable)
    
    Buick 1932
    Dodge 1999
    Fiat 1988
    Ford 1932
    Ford 1992
    Honda 1977
    
    Array - Sorted by Year (Ascending - IComparer)
    
    Ford 1932
    Buick 1932
    Honda 1977
    Fiat 1988
    Ford 1992
    Dodge 1999
    
    Array - Sorted by Make (Descending - IComparer)
    
    Honda 1977
    Ford 1932
    Ford 1992
    Fiat 1988
    Dodge 1999
    Buick 1932
    
    Array - Sorted by Year (Descending - IComparer)
    
    Dodge 1999
    Ford 1992
    Fiat 1988
    Honda 1977
    Buick 1932
    Ford 1932