W3docs

Les modificateurs non-accès en Java

Utilisez les modificateurs non-accès Java — static, final, abstract, synchronized, transient, volatile — et ce que chacun contrôle.

Les modificateurs d'accès Java — public, protected, private — contrôlent qui peut voir un membre. Les modificateurs non-accès contrôlent comment il se comporte. Ce sont quelques mots-clés qui changent la propriété, la mutabilité, le multithreading, la sérialisation et quelques autres aspects. Ce chapitre fait office de carte ; chaque modificateur dispose d'un chapitre ou d'une section plus complète ailleurs.

La liste complète

ModificateurS'applique àCe qu'il fait
staticchamps, méthodes, classes imbriquées, blocsAppartient à la classe, pas aux instances
finalclasses, méthodes, champs, paramètres, variables localesNe peut pas être réassigné/surchargé/étendu
abstractclasses, méthodesPas de corps / ne peut pas être instancié ; doit être implémenté par une sous-classe
synchronizedméthodes, blocsUn seul thread à la fois peut l'exécuter sur un verrou donné
volatilechampsLes lectures/écritures ne sont pas mises en cache dans la mémoire locale du thread
transientchampsIgnoré par la sérialisation par défaut
nativeméthodesL'implémentation réside dans du code non-Java (généralement C/C++)
strictfpclasses, méthodesForce un comportement flottant IEEE-754 strict (principalement historique)
defaultméthodes d'interfaceFournit un corps par défaut dans une interface
sealed / non-sealedclasses, interfacesRestreint les classes qui peuvent étendre (Java 17+)

Vous rencontrerez constamment static, final, abstract et default. Les autres n'apparaissent que lorsque leur problème se pose.

static — appartient à la classe

Un membre static est associé à la classe elle-même, et non à une instance particulière :

public class Counter {
  int instanceCount;          // one per Counter object
  static int classCount;      // one shared by everyone
}

static est si courant qu'il possède son propre chapitre — voir java-static.

final — ne peut pas changer

final signifie « cette liaison est fixée une fois définie ». Il s'applique à plusieurs choses différentes :

final int MAX = 100;          // local variable cannot be reassigned
public final class Money {}   // class cannot be extended
public final void close() {}  // method cannot be overridden
private final int balance;    // field assigned once, then immutable

final est le fondement des constantes (static final), des objets immuables et d'une conception d'héritage sûre. Traitement complet dans java-final.

abstract — n'a pas de corps, doit être rempli

abstract appliqué à une classe signifie « vous ne pouvez pas instancier cela directement — seulement les sous-classes. » Appliqué à une méthode, cela signifie « pas de corps ici — chaque sous-classe concrète doit en fournir un » :

public abstract class Shape {
  public abstract double area();      // no body
}

public class Circle extends Shape {
  double r;
  public double area() { return Math.PI * r * r; }
}

new Shape() est une erreur de compilation ; new Circle() fonctionne. Traité dans classes abstraites.

synchronized — un thread à la fois

Lorsque deux threads peuvent appeler la même méthode sur le même objet, marquer la méthode synchronized garantit qu'un seul s'exécute à la fois :

public synchronized void deposit(int amount) {
  balance += amount;
}

C'est la forme la plus simple de verrouillage. Il y a une section entière sur la concurrence plus loin dans le livre ; pour l'instant, reconnaissez que le mot-clé existe et ce qu'il fait globalement. Voir synchronisation pour l'histoire complète.

volatile — visible entre les threads

Sans volatile, les threads sont autorisés à mettre en cache la valeur d'un champ. Les lectures dans un thread pourraient ne jamais voir les écritures d'un autre :

private volatile boolean stopped = false;

volatile force chaque lecture à venir de la mémoire principale et chaque écriture à y aller. C'est le cousin léger de synchronized pour les champs indicateurs simples — voir volatile pour les détails du modèle mémoire.

transient — ignoré lors de la sérialisation

La sérialisation d'objets intégrée de Java (Serializable) écrit tous les champs par défaut. transient dit « n'inclus pas celui-ci » — généralement utilisé pour les caches, les valeurs calculées ou les choses qui n'ont pas de sens en dehors du programme en cours d'exécution :

public class Session {
  String userId;
  transient String passwordHash;     // not serialized
}

Le code moderne utilise les sérialiseurs JSON plus que Serializable, mais le mot-clé est toujours utile dans les bibliothèques qui en tiennent compte. Plus d'informations dans sérialisation.

native — implémenté ailleurs

native est pour les méthodes dont le corps est dans un autre langage (C/C++ via JNI). Vous les écrivez rarement vous-même ; vous ne les voyez que dans les bibliothèques de bas niveau :

public native int currentTimeMillis();

strictfp — virgule flottante stricte

À l'origine, strictfp forçait une arithmétique à virgule flottante IEEE-754 prévisible entre plateformes. À partir de Java 17, toutes les mathématiques en virgule flottante sont implicitement strictes, ce qui rend le mot-clé sans effet. Vous pouvez l'ignorer dans la plupart des cas ; il subsiste dans les bases de code plus anciennes.

default — sur les méthodes d'interface

Dans une interface, default vous permet de fournir un corps pour une méthode au lieu de la laisser abstraite :

public interface Greeter {
  default String greet(String name) {
    return "Hello, " + name;
  }
}

Sans default, une méthode d'interface n'a pas de corps et chaque classe implémentante doit écrire la sienne. Traitement complet dans méthodes par défaut.

sealed et non-sealed

Une classe sealed nomme la liste exacte des classes autorisées à l'étendre. Les sous-classes doivent ensuite choisir d'être final, sealed ou non-sealed :

public sealed class Shape permits Circle, Square { }
public final class Circle extends Shape { }
public non-sealed class Square extends Shape { }

Utile pour les hiérarchies de types fermées — voir classes scellées.

Combiner les modificateurs

Vous pouvez généralement empiler les modificateurs librement, dans cet ordre conventionnel :

public  static  final   int MAX = 100;
private static  volatile int counter;
protected abstract       void onInit();

Certaines combinaisons sont illégales : une méthode ne peut pas être à la fois abstract et final, à la fois abstract et private, ou à la fois abstract et static. Le compilateur vous le dira lorsque vous aurez franchi une limite.

Un exemple concret

java— editable, runs on the server

Et ensuite

Les deux prochains chapitres approfondissent les deux modificateurs que vous utiliserez le plus souvent : static pour les membres au niveau de la classe, puis final pour l'immuabilité. Lisez-les dans l'ordre.

Pratique

Pratique
Quel modificateur non-accès signifie qu'un membre de classe appartient à la classe elle-même plutôt qu'à chaque instance ?
Quel modificateur non-accès signifie qu'un membre de classe appartient à la classe elle-même plutôt qu'à chaque instance ?
Was this page helpful?