Notes
L’accès à cette page nécessite une autorisation. Vous pouvez essayer de vous connecter ou de modifier des répertoires.
L’accès à cette page nécessite une autorisation. Vous pouvez essayer de modifier des répertoires.
Cet article montre comment utiliser les interfaces et les IEnumerable
IEnumerator
interfaces pour créer une classe que vous pouvez utiliser dans une foreach
instruction.
Version du produit d’origine : Visual Studio
Numéro de base de connaissances d’origine : 322022
Interface IEnumerator
IEnumerable
et IEnumerator
sont fréquemment utilisés ensemble. Bien que ces interfaces soient similaires (et ont des noms similaires), elles ont des objectifs différents.
L’interface IEnumerator
fournit une fonctionnalité itérative pour une collection interne à une classe. IEnumerator
exige que vous implémentez trois méthodes :
La
MoveNext
méthode, qui incrémente l’index de collection de 1 et retourne un bool qui indique si la fin de la collection a été atteinte.Méthode
Reset
, qui réinitialise l’index de collection à sa valeur initiale de -1. Cela invalide l’énumérateur.Méthode
Current
, qui retourne l’objet actuel àposition
.public bool MoveNext() { position++; return (position < carlist.Length); } public void Reset() { position = -1; } public object Current { get { return carlist[position];} }
Interface IEnumerable
L’interface IEnumerable
prend en charge l’itération foreach
. IEnumerable
exige que vous implémentez la GetEnumerator
méthode.
public IEnumerator GetEnumerator()
{
return (IEnumerator)this;
}
Quand utiliser l’interface
Au départ, il peut être déroutant d’utiliser ces interfaces. L’interface IEnumerator
fournit une itération sur un objet de type collection dans une classe. L’interface IEnumerable
autorise l’énumération à l’aide d’une foreach
boucle. Toutefois, la GetEnumerator
méthode de l’interface IEnumerable
retourne une IEnumerator
interface. Ainsi, pour implémenter IEnumerable
, vous devez également implémenter IEnumerator
. Si vous n’implémentez IEnumerator
pas, vous ne pouvez pas convertir la valeur de retour de la GetEnumerator
méthode de IEnumerable
l’interface IEnumerator
.
En résumé, l’utilisation de IEnumerable
nécessite que la classe implémente IEnumerator
. Si vous souhaitez fournir une prise en charge, foreach
implémentez les deux interfaces.
Exemple étape par étape
L’exemple suivant montre comment utiliser ces interfaces. Dans cet exemple, les interfaces et IEnumerable
les IEnumerator
interfaces sont utilisées dans une classe nommée cars
. La cars
classe a un tableau interne d’objets car
. Les applications clientes peuvent énumérer ce tableau interne à l’aide d’une foreach
construction en raison de l’implémentation de ces deux interfaces.
Procédez comme suit pour créer un projet d’application console dans Visual C# :
- Démarrez Microsoft Visual Studio .NET ou Visual Studio.
- Dans le menu Fichier , pointez sur Nouveau, puis cliquez sur Projet.
- Cliquez sur Projets Visual C# sous Types de projets, puis sur Application console sous Modèles.
- Dans la zone Nom , tapez ConsoleEnum.
Renommez Class1.cs en host.cs, puis remplacez le code dans host.cs par le code suivant :
using System; namespace ConsoleEnum { class host { [STAThread] static void Main(string[] args) { cars C = new cars(); Console.WriteLine("\nInternal Collection (Unsorted - IEnumerable,Enumerator)\n"); foreach(car c in C) Console.WriteLine(c.Make + "\t\t" + c.Year); Console.ReadLine(); } } }
Dans le menu Projet , cliquez sur Ajouter une classe, puis tapez la voiture dans la zone Nom .
Remplacez le code dans car.cs par le code suivant :
using System; using System.Collections; namespace ConsoleEnum { public class car { 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;} } }//end class }//end namespace
Dans le menu Projet , cliquez sur Ajouter une classe pour ajouter une autre classe au projet, puis tapez des voitures dans la zone Nom .
Remplacez le code dans cars.cs par le code suivant :
using System; using System.Collections; namespace ConsoleEnum { public class cars : IEnumerator,IEnumerable { private car[] carlist; int position = -1; //Create internal array in constructor. public cars() { carlist= 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) }; } //IEnumerator and IEnumerable require these methods. public IEnumerator GetEnumerator() { return (IEnumerator)this; } //IEnumerator public bool MoveNext() { position++; return (position < carlist.Length); } //IEnumerable public void Reset() { position = -1; } //IEnumerable public object Current { get { return carlist[position];} } } }
Exécutez le projet .
La sortie suivante s’affiche dans la fenêtre console :
Ford 1992
Fiat 1988
Buick 1932
Ford 1932
Dodge 1999
Honda 1977
Bonnes pratiques
L’exemple de cet article est conservé aussi simple que possible pour mieux expliquer l’utilisation de ces interfaces. Pour rendre le code plus robuste et s’assurer que le code utilise les recommandations actuelles en matière de bonnes pratiques, modifiez le code comme suit :
- Implémentez
IEnumerator
dans une classe imbriquée afin de pouvoir créer plusieurs énumérateurs. - Fournir la gestion des exceptions pour la
Current
méthode deIEnumerator
. Si le contenu de la collection change, lareset
méthode est appelée. Par conséquent, l’énumérateur actuel est invalidé et vous recevez uneIndexOutOfRangeException
exception. D’autres circonstances peuvent également provoquer cette exception. Implémentez donc unTry...Catch
bloc pour intercepter cette exception et déclencher uneInvalidOperationException
exception.
using System;
using System.Collections;
namespace ConsoleEnum
{
public class cars : IEnumerable
{
private car[] carlist;
//Create internal array in constructor.
public cars()
{
carlist= 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)
};
}
//private enumerator class
private class MyEnumerator:IEnumerator
{
public car[] carlist;
int position = -1;
//constructor
public MyEnumerator(car[] list)
{
carlist=list;
}
private IEnumerator getEnumerator()
{
return (IEnumerator)this;
}
//IEnumerator
public bool MoveNext()
{
position++;
return (position < carlist.Length);
}
//IEnumerator
public void Reset()
{
position = -1;
}
//IEnumerator
public object Current
{
get
{
try
{
return carlist[position];
}
catch (IndexOutOfRangeException)
{
throw new InvalidOperationException();
}
}
}
} //end nested class
public IEnumerator GetEnumerator()
{
return new MyEnumerator(carlist);
}
}
}