Accueil
Java Standard Edition
Java EE 5
Visual Basic .Net 2005
Visual C++ .Net 2005
Visual C# .Net 2005
Cours ASP .Net 2.0
Postgresql
Linux
Visual Studio 2008
ASP 3.0 Classique
Cours Javascript - DOM - DHTML
Cours Ajax
VBA
Assembleur
Perl
Membres
L'auteur du site
Nouveautés sur le site
Contacts
Plan du site
Exécution d'un programme
Les archives Jar
Les classes abstraites
Les interfaces
Les tableaux
La généricité
Les énumérations
Les classes internes
Classes anonymes et internes locales
Les threads: généralités
Les threads(2): synchronisation
E/S(1):InputStream et OutputStream
E/S(2):FileInputStream et FileOutputStream
E/S(3):Reader et Writer
E/S(4):FilterInputStream et FilterOutputStream
E/S(5):Les filtres d'octets: PrintStream
E/S(6):Les filtres d'octets: DataInputStream et DataOutputStream
E/S(7):Les filtres d'octets: BufferedInputStream et BufferedOutputStream
E/S(8):Flux de caractères: PrintWriter
E/S(9):Flux de caractères: FilterReader et FilterWriter
E/S(10):Flux de caractères: InputStreamReader, OutputStreamWriter, StreamDecoder, StreamEncoder
E/S(11):Flux de caractères: BufferedReader et BufferedWriter
E/S(12):Flux de caractères: FileReader et FileWriter
La classe String (java.lang)
Les collections: L'interface Collection(java.lang)
Les collections(2): L'interface List(java.util)
Les collections(3): AbstractCollection(java.util)
Les collections(4): AbstractList(java.util)
Les collections(5): Vector(java.util)
Les collections(6): L'interface Map(java.util)
Les collections(7): AbstractMap(java.util)
Les collections(8): HashMap(java.util)
La bibliothèque Swing en Java
Les bases de données en Java
JDBC ( Java Database Connectivity )
Les interfaces graphiques
Les fichiers de configuration en Java
INSTALLATION JAVA EE 5, JRE 6, ECLIPSE, TOMCAT, ETC SOUS LINUX
INSTALLATION JAVA EE 5, JRE 6, ECLIPSE, TOMCAT, ETC SOUS WINDOWS
Les applications Web en java
Les filtres Java (javax.servlet.Filter)
I Généralités
I.1 Le formulaire principal
I.2 Les objets créés par Visual
I.3 Les variables références
I.4 Le garbage collector
II Créer évènements
II.1 Rappel évènements
II.2 Procédure à suivre
II.2.1 Créer son EventArgs
II.2.2 Créer EmetEvent
II.2.3 Déclarations autres
I Généralités
I.1 Applications winforms
I.2 Applications MFC
I.3 Objets managés ou pas
I.4 Objets non managés
I.5 Objets managés - handle
I.6 Le top-level ^
II Créer évènements
II.1 Rappel évènements
II.2 Procédure à suivre
II.2.1 Créer son EventArgs
II.2.2 Créer EmetEvent
II.2.3 Déclarations autres
I Généralités
I.1 Puissant et Accessible
I.2 Créer ses classes
II Créer évènements
II.1 Rappel évènements
II.2 Procédure à suivre
III Les services Windows
IV Le .net remoting
V Communication Tcp avec TcpClient et TcpListener
II.2.1 Créer son EventArgs
II.2.2 Créer EmetEvent
II.2.3 Déclarations autres
I Généralités
I.1 Un EDI formidable
I.2 Inclure C# ou VB
I.3 L'objet Response
I.4 Les évènements
II ASP .net et les bdd
II.1 Essayer plusieurs fois la requête
I 2.1 Fichiers distincts
I.2.2 Avec la balise script
I.2.3 Inclure réellement
I.2.4 Avec Response.Write()
I.3.1 La méthode Response.Redirect()
I.4.1 Résoudre problème post
Installation Postgre Linux
Cours Postgresql
Le Shell Unix( Linux, Ubuntu)
Les scripts C-Shell
Programmation système Unix
Reseau Linux
Les iptables
Windows Presentation Foundation(WPF)
Le Framework 3.0
Windows Workflow Foundation(WF)
ASP 3.0 Classique
Cours Javascript - DOM - DHTML
Chat Ajax
VBA Excel 2003
Assembleur
Perl
Inscription
Liste membres
Livre d'or
Forum
Accueil
>
Java Standard Edition
>
Les classes internes
____________________________________________________________________________________________________
Connexion
Java - Les classes internes
Sommaire :
I) Définition des classes internes
II) Les classes internes non statiques (inner class ou non static nested class)
III) Les classes internes statiques( static nested class)
IV) Les classes internes locales et les classes anonymes
V)Code source du projet d'exemple
V-1) Classe Femme (package humain)
V-2) Classe Main( package main)
VI)Téléchargement du projet d'exemple
I) Définition des classes internes
Les classes internes existent depuis Java Standard 1.1
Regardons cet extrait du site de sun:
"Terminology: Nested classes are divided into two categories: static and non-static. Nested classes that are declared static are simply called static nested classes. Non-static nested classes are called inner classes."
II) Les classes internes non statiques (inner class ou non static nested class)
Une classe interne est une classe écrite à l'intérieur d'une autre classe. Voyez l'exemple ci-dessous.
Ici la classe Enfant est déclarée à l'intérieur de la classe Femme. La classe n'est pas statique car il n'y a pas le mot-clé static lors de la déclaration de la classe. Ceci implique que les membres de la classe englobante(ici Femme) sont accessibles depuis la classe Enfant.
Une instance de la classe englobante est toujours attachée à l'instance de la classe interne, c'est la règle absolue des classes internes non statiques. L'objet interne est DANS l'objet englobant, il restera toujours lié ainsi à son objet englobant("enclosing" en anglais). D'ailleurs, à partir d'une classe extérieure, comme Main ici, on ne peut pas faire de new Femmme.Enfant, car on essaye de créer un objet enfant sans indiquer d'objet englobant. Un enfant doit toujours possèder une mère!
Il existe une syntaxe spéciale pour pouvoir le faire:
//(classe Main) Femme murielle = new Femme("murielle"); //(...) Femme.Enfant abdel = murielle.new Enfant("abdel"); //on crée un enfant de murielle
Cette syntaxe permet de préciser l'instance de Femme englobant l'objet enfant.
Ainsi on est certain que lorsque les méthodes de la classe Enfant essaieront d'accéder à des attributs et méthodes d'instance de la classe englobante, elles auront bien un objet Femme englobant.
Le code de l'exemple n'est pas sécurisé volontairement: j'aurais pu mettre en privé la classe Enfant, et on aurait accéder aux enfants de la femme qu'à travers des méthodes, sans jamais donner l'objet enfant, mais les caractéristiques concernées(comme le prénom de l'enfant).
Les classes internes sont d'ailleurs les seules classes qui peuvent être privées.
J'aurais pu mettre le tableau d'enfants en privé, un accesseur getter sur le nombre d'enfants, etc.
Remarque: il est possible, dans la classe Main, de faire un import Femme.Enfant , et ainsi on peut écrire Enfant au lieu de Femme.Enfant( personnellement je ne préfère pas). Dans la classe englobante et la classe interne, on peut écrire Enfant directement, sans avoir besoin du import ou de Femme.Enfant .
Dans la classe Enfant, pour accéder aux attributs de la classe Femme, on écrit le nom de l'attribut, tout simplement. Par exemple:
nbEnfants++;
Et non pas this.nbEnfants, car this ici désigne l'objet courant de la classe Enfant.
Si un attribut du même nom existe dans la classe Enfant, on utilise la syntaxe:
Femme.this.nbEnfants : le nom de la classe englobante, suivi de ".this.attribut".
Remarque: On ne peut pas déclarer de membres static dans une classe interne non statique. Par exemple, impossible d'ajouter l'attribut "public static Integer monAttrSt;".
III) Les classes internes statiques( static nested class)
Un extrait du site sun:
"In effect, a static nested class is behaviorally a top-level class that has been nested in another top-level class for packaging convenience."
"top-level" est une classe de premier niveau, c'est-à-dire la classe contenant la classe interne.
Une classe interne static, comme tout membre non static d'une classe, ne peut pas accéder aux membres d'instance de la classe englobante.
On accède à la classe interne par nomClasseTopLevel.NomClasseInterne. On peut aussi faire un import monPackage.nomClasseTopLevel.NomClasseInterne, pour pouvoir utiliser directement NomClasseInterne(je déconseille).
Une classe interne non static est en fait une classe de premier niveau qui a été mis à l'intérieur d'une classe top-level pour des avantages d'empaquetage. C'est-à-dire qu'on veut obliger l'utilisateur, à chaque fois qu'il utilise la classe, à préciser avant le nom de la classe top-level. Ceci à pour effet que c'est comme si la classe interne se trouvait dans un package dont le nom serait la classe englobante, il n'y a pas plus d'effets que cela.
IV) Les classes internes locales et les classes anonymes
Une classe interne locale est une classe interne non static (inner class) déclarée à l'intérieur d'une méthode. Et une classe anonyme est une classe interne locale, mais qui ne possède pas de nom. Un chapitre entier est consacré à ces deux types de classes.
V)Code source du projet d'exemple
V-1) Classe Femme (package humain)
package humain; public class Femme { public Enfant[] enfants; public int nbEnfants; public String prenom; public Femme(String pPrenom) { this.prenom=pPrenom; this.nbEnfants = 0; this.enfants = new Enfant[6]; //on prévoit 6 enfants max } /** * Cette classe est une classe interne * non static(inner class ou non static nested class) */ public class Enfant { public String prenom; public Enfant(String pPrenom) { if (Femme.this.nbEnfants<6) { nbEnfants++; enfants[nbEnfants-1] = this; this.prenom = pPrenom; } } //fin constructeur } //fin classe interne Enfant /** * * Cette classe est une classe interne static * (static nested class) * */ public static class EnfantStatic { public String prenom; public EnfantStatic(String pPrenom) { this.prenom = pPrenom; } //fin constructeur } public void ajouterEnfant(String pPrenom) { Enfant nveauEnfant = new Enfant(pPrenom); } public void afficherListeEnfants() { System.out.println("Nb d'enfants: "+this.nbEnfants); for (int i=0;i<this.nbEnfants;i++) { System.out.println("Prénom: "+this.enfants[i].prenom); } } public Enfant getEnfant(int pNum) { if (pNum>this.nbEnfants-1) { throw new IndexOutOfBoundsException("Il y a "+this.nbEnfants+" enfants"); } else if (pNum<1) { throw new IndexOutOfBoundsException("Numéro doit être = 1 au moins"); } else { return this.enfants[pNum]; } } } //fin classe Femme
V-2) Classe Main( package main)
package main; import humain.*; //il est possible de faire import humain.Femme.Enfant, et après on peut utiliser directement Enfant /** * TestClassesInternes * Programme d'exemple pour les classes internes * Les classes ne sont pas sécurisées volontairement pour * l'exemple * @version 1.0 , 25/10/2008 * @author sabri koffler * */ public class Main { /** * @param args */ public static void main(String[] args) { Femme murielle = new Femme("murielle"); murielle.ajouterEnfant("pierre"); murielle.ajouterEnfant("paul"); murielle.ajouterEnfant("marie"); // murielle.afficherListeEnfants(); // Femme.Enfant enf = murielle.getEnfant(2); System.out.println("Enfant indice 2: " + enf.prenom); //Femme.Enfant testEnf = new Femme.Enfant("bebe"); //erreur "No enclosing instance of type Femme //is accessible. Must qualify the allocation with //an enclosing instance of type Femme(e.g. x.new A() where //x is an instance of Femme) Femme.Enfant abdel = murielle.new Enfant("abdel"); //on crée un enfant de murielle murielle.nbEnfants++; murielle.enfants[3] = abdel; enf = murielle.getEnfant(3); System.out.println("Enfant indice 3(nouveau): " + enf.prenom); // //Exemple classe interne static Femme.EnfantStatic enfStat = new Femme.EnfantStatic("julien"); System.out.println("Prénom de l'enfant: " + enfStat.prenom); } }
VI)Téléchargement du projet d'exemple
Projet d'exemple, V1.1
RETOUR HAUT