Les classes internes ne sont pas très faciles à comprendre, mais en clair, il s'agit simplement d'une classe qui contient une autre classe.
Tout comme une personne est composée de structures corporelles telles que le cerveau, les membres et les organes, une classe interne est équivalente à l'un de ces organes, comme le cœur : elle possède aussi ses propres propriétés et comportements (sang, battement).
De toute évidence, un cœur ne peut pas être représenté uniquement par des propriétés ou des méthodes ; il nécessite une classe.
Et le cœur est à l'intérieur du corps humain, tout comme une classe interne est à l'intérieur de sa classe externe.
Exemple 1 : Structure de base d'une classe interne
//外部类
class Out {
private int age = 12;
//内部类
class In {
public void print() {
System.out.println(age);
}
}
}
public class Demo {
public static void main(String[] args) {
Out.In in = new Out().new In();
in.print();
//或者采用下种方式访问
/*
Out out = new Out();
Out.In in = out.new In();
in.print();
*/
}
}
Sortie : 12
Il n'est pas difficile de voir, à partir de l'exemple ci-dessus, que les classes internes nuisent en réalité gravement à une bonne structure de code, mais pourquoi continuer à les utiliser ?
Parce qu'une classe interne peut utiliser librement les variables membres de la classe externe (y compris celles privées) sans créer un objet de la classe externe ; c'est aussi le seul avantage des classes internes.
Tout comme le cœur peut accéder directement au sang du corps, plutôt que de demander à un médecin de prélever du sang.
Après la compilation du programme, deux fichiers .class sont générés, à savoir Out.class et Out$In.class.
Ici, $ représente le point dans Out.In dans le programme ci-dessus.
Out.In in = new Out().new In()On peut l'utiliser pour créer un objet de la classe interne. Avec cette approche, il y a deux petits points à noter :
- 1. Le Out au début sert à indiquer à quelle classe externe appartient l'objet de la classe interne à créer.
- 2. Vous devez d'abord disposer d'un objet de la classe externe avant de pouvoir créer un objet de la classe interne, car le but de la classe interne est d'accéder aux variables membres de la classe externe.
class Out {
private int age = 12;
class In {
private int age = 13;
public void print() {
int age = 14;
System.out.println("局部变量:" + age);
System.out.println("内部类变量:" + this.age);
System.out.println("外部类变量:" + Out.this.age);
}
}
}
public class Demo {
public static void main(String[] args) {
Out.In in = new Out().new In();
in.print();
}
}Sortie :
局部变量:14 内部类变量:13 外部类变量:12
D'après l'exemple 1, on peut voir que lorsqu'il n'y a pas de variables membres ou de variables locales portant le même nom, la classe interne accède directement aux variables membres de la classe externe sans qu'il soit nécessaire de spécifierOut.this.propertyName。
Sinon, les variables locales de la classe interne masqueront les variables membres de la classe externe.
Pour accéder aux variables membres propres à la classe interne, vous pouvez utiliserthis.propertyName, et pour accéder aux variables membres de la classe externe, vous devez utiliserOut.this.propertyName。
Exemple 3 : classe interne statique
class Out {
private static int age = 12;
static class In {
public void print() {
System.out.println(age);
}
}
}
public class Demo {
public static void main(String[] args) {
Out.In in = new Out.In();
in.print();
}
}Sortie : 12
On peut voir que si vous utilisez static pour rendre la classe interne statique, alors la classe interne ne peut accéder qu'aux variables membres statiques de la classe externe, ce qui est une limitation.
Deuxièmement, parce que la classe interne est rendue statique, Out.In peut être traité comme un tout, et vous pouvez directement créer un objet de la classe interne avec new (accéder aux membres statiques via le nom de la classe ; peu importe qu'un objet de la classe externe soit créé).
Exemple 4 : classe interne privée/h3>class Out {
private int age = 12;
private class In {
public void print() {
System.out.println(age);
}
}
public void outPrint() {
new In().print();
}
}
public class Demo {
public static void main(String[] args) {
//此方法无效
/*
Out.In in = new Out().new In();
in.print();
*/
Out out = new Out();
out.outPrint();
}
}
Sortie : 12
Si une classe interne est destinée à être manipulée uniquement par des méthodes de la classe externe, alors vous pouvez déclarer la classe interne comme private.
Dans le code ci-dessus, nous devons créer un objet de la classe In à l'intérieur de la classe Out pour pouvoir l'utiliser, et nous ne pouvons plus utiliserOut.In in = new Out().new In()pour créer un objet de la classe interne.
En d'autres termes, à ce stade, la classe interne ne peut être contrôlée que par la classe externe.
Tout comme mon cœur ne peut être contrôlé que par mon corps ; les autres personnes ne peuvent pas y accéder directement.
Exemple 5 : classe interne locale à une méthode
class Out {
private int age = 12;
public void Print(final int x) {
class In {
public void inPrint() {
System.out.println(x);
System.out.println(age);
}
}
new In().inPrint();
}
}
public class Demo {
public static void main(String[] args) {
Out out = new Out();
out.Print(3);
}
}
Sortie :
3 12
Dans le code ci-dessus, nous avons déplacé la classe interne dans une méthode de la classe externe, puis créé un objet de la classe interne à l'intérieur de la méthode de la classe externe pour appeler la méthode de la classe interne.
Si nous devons passer des paramètres dans la méthode de la classe externe à ce stade, alors les paramètres de méthode de la classe externe doivent être définis avec final.
Quant à final, il n'a pas de signification particulière ici ; ce n'est qu'une formalité.