Classes statiques en Java

947

Y a-t-il quelque chose comme static classen java?

Quel est le sens d'une telle classe. Toutes les méthodes de la classe statique doivent-elles l'être staticégalement?

Est-il obligatoire dans l'autre sens, que si une classe contient toutes les méthodes statiques, la classe doit-elle aussi être statique?

À quoi servent les classes statiques?

Kraken
la source
4
Vous pourriez être intéressé par stackoverflow.com/questions/3584113/java-static-class
Ishtar
Les classes statiques sont essentiellement utilisées pour regrouper des classes.
RockingDev

Réponses:

847

Java a des classes imbriquées statiques , mais il semble que vous recherchiez une classe statique de niveau supérieur. Java n'a aucun moyen de rendre statique une classe de niveau supérieur, mais vous pouvez simuler une classe statique comme celle-ci:

  • Déclarez votre classe final- Empêche l'extension de la classe car l'extension d'une classe statique n'a aucun sens
  • Make the constructor private- Empêche l'instanciation par le code client car cela n'a aucun sens d'instancier une classe statique
  • Créer tous les membres et fonctions de la classe static- Étant donné que la classe ne peut pas être instanciée, aucune méthode d'instance ne peut être appelée ni aucun champ d'instance accessible
  • Notez que le compilateur ne vous empêchera pas de déclarer un membre d'instance (non statique). Le problème n'apparaîtra que si vous essayez d'appeler le membre de l'instance

Exemple simple par suggestions ci-dessus:

public class TestMyStaticClass {
     public static void main(String []args){
        MyStaticClass.setMyStaticMember(5);
        System.out.println("Static value: " + MyStaticClass.getMyStaticMember());
        System.out.println("Value squared: " + MyStaticClass.squareMyStaticMember());
        // MyStaticClass x = new MyStaticClass(); // results in compile time error
     }
}

// A top-level Java class mimicking static class behavior
public final class MyStaticClass {
    private MyStaticClass () { // private constructor
        myStaticMember = 1;
    }
    private static int myStaticMember;
    public static void setMyStaticMember(int val) {
        myStaticMember = val;
    }
    public static int getMyStaticMember() {
        return myStaticMember;
    }
    public static int squareMyStaticMember() {
        return myStaticMember * myStaticMember;
    }
}

À quoi servent les classes statiques? Une bonne utilisation d'une classe statique consiste à définir des classes ponctuelles, utilitaires et / ou de bibliothèque où l'instanciation n'aurait pas de sens. Un bon exemple est la classe Math qui contient des constantes mathématiques telles que PI et E et fournit simplement des calculs mathématiques. Exiger l'instanciation dans un tel cas serait inutile et déroutant. Voir la Mathclasse et le code source . Notez que c'est le cas finalet que tous ses membres le sont static. Si Java permettait de déclarer des classes de niveau supérieur, staticla classe Math serait en effet statique.

Paul Sasik
la source
35
une classe Fooavec seulement des staticméthodes n'est pas la même chose questatic class Foo
craigb
12
@Evorlor: Si une classe est déclarée finale, ses méthodes sont automatiquement (effectivement) finales. En effet, une classe finale ne peut pas être sous-classée et ses méthodes ne peuvent donc pas être remplacées (c'est-à-dire qu'elles sont effectivement finales). docs.oracle.com/javase/tutorial/java/IandI/final.html
jwayne
30
Cette réponse traite peut-être de la signification de l'OP, mais elle n'explique pas (actuellement) les classes statiques Java et ne répond donc pas du tout à la question! C'est très mauvais pour les gens qui arrivent ici en essayant de comprendre ce que signifie une classe statique en Java.
Tom
12
@JBoy: Il existe une chose telle que la "classe statique" en Java, c'est la question, mais cette réponse ne l'explique pas du tout. Au lieu de cela, il explique comment simuler en Java ce que la réponse appelle une "classe statique" - mais ce n'est pas ce qu'est une "classe statique" en Java! (C'est peut-être ce qu'on appelle une "classe statique" dans d'autres langages, mais les gens qui viennent ici pour en savoir plus sur les classes statiques Java seront induits en erreur et confus.)
Tom
4
vous devez mentionner explicitement que MyStaticClass () {// private constructor myStaticMember = 1; } n'aura AUCUN effet puisque le constructeur ne sera pas appelé. Mais ce n'est pas l'essentiel. Je suis encore très confus quant à l'utilité des classes internes statiques en Java et leur utilité ou valeur ajoutée.
moldave
316

Eh bien, Java a des "classes imbriquées statiques", mais elles ne sont pas du tout les mêmes que les classes statiques de C #, si c'est de là que vous veniez. Une classe imbriquée statique n'est qu'une classe qui n'a pas implicitement une référence à une instance de la classe externe.

Les classes imbriquées statiques peuvent avoir des méthodes d'instance et des méthodes statiques.

Il n'y a rien de tel qu'une classe statique de niveau supérieur en Java.

Jon Skeet
la source
12
En Java Pourquoi la classe imbriquée statique autorise-t-elle les méthodes d'instance? Quelle est l'utilité d'une méthode d'instance dans une telle classe?
Geek
19
@Geek: Avez-vous lu ma réponse? Lisez attentivement la deuxième phrase. Pourquoi ne voudriez-vous pas pouvoir avoir des méthodes d'instance de classes statiques? Vous pouvez en créer des instances, après tout.
Jon Skeet
17
@Geek: Oui, c'est tout à fait permis. Votre "compréhension" que les classes statiques sont des classes utilitaires est incorrecte, fondamentalement. Ce n'est pas du tout ce que signifient les classes statiques en Java.
Jon Skeet
14
@ Geek: Oui. Exactement comme je l'ai écrit dans ma réponse: "Une classe imbriquée statique n'est qu'une classe qui n'a pas implicitement une référence à une instance de la classe externe."
Jon Skeet
6
@KhurramAli: Voulez-vous dire implicitement ? Ils ne sont certainement pas explicitement statiques, étant donné que vous n'utilisez pas le mot-clé staticpour les déclarer. Ils sont implicitement statiques dans la mesure où vous n'avez besoin d'aucune référence à quoi que ce soit d'autre pour en construire une. Personnellement, je trouve la terminologie statique / non statique un peu étrange pour les classes imbriquées de toute façon ... Je pense qu'il serait plus simple de parler de ce comportement.
Jon Skeet
157

Il existe une classe imbriquée statique , cette classe [imbriquée statique] n'a pas besoin d'une instance de la classe englobante pour être instanciée elle-même.

Ces classes [celles qui sont imbriquées statiques] ne peuvent accéder qu'aux membres statiques de la classe englobante [car elles n'ont aucune référence aux instances de la classe englobante ...]

exemple de code:

public class Test { 
  class A { } 
  static class B { }
  public static void main(String[] args) { 
    /*will fail - compilation error, you need an instance of Test to instantiate A*/
    A a = new A(); 
    /*will compile successfully, not instance of Test is needed to instantiate B */
    B b = new B(); 
  }
}
amit
la source
1
Pouvons-nous donc dire que nous pouvons utiliser des classes statiques internes afin de les instancier sans avoir besoin de les rendre publiques?
moldave
@moldovean Nous utilisons des classes statiques internes afin de les instancier à partir d'un contexte statique (tel que main). Je ne pense pas que cela ait à voir avec la visibilité.
Michael Dorst
2
@moldovean statique / non statique est orthogonal à la visibilité. Vous pouvez avoir tout type de visibilité avec statique ou non statique. Le fait est, avez-vous besoin d'une instance de la classe englobante, afin de créer la classe interne?
Amit
103

Oui, il existe une classe imbriquée statique en java. Lorsque vous déclarez une classe imbriquée statique, elle devient automatiquement une classe autonome qui peut être instanciée sans avoir à instancier la classe externe à laquelle elle appartient.

Exemple:

public class A
{

 public static class B
 {
 }
}

Parce que class Best déclaré statique, vous pouvez explicitement instancier:

B b = new B();

Notez que s'il class Bn'a pas été déclaré statique pour le rendre autonome, un appel d'objet d'instance aurait ressemblé à ceci:

A a= new A();
B b = a.new B();
Bitmap
la source
7
notez que vous pouvez instancier la classe non statique régulièrement comme B b = new B();si vous essayez de l'instancier à partir de la classe Aelle-même.
Muhammed Refaat
33

Que se passe-t-il lorsqu'un membre à l'intérieur d'un classest déclaré comme static..? Les membres sont accessibles sans instancier le class. Par conséquent, créer une classe externe (classe de niveau supérieur) staticn'a aucun sens. Ce n'est donc pas autorisé.

Mais vous pouvez définir des classes internes comme statiques (car c'est un membre de la classe de niveau supérieur). Ensuite, cette classe est accessible sans instancier la classe de niveau supérieur. Prenons l'exemple suivant.

public class A {
    public static class B {

    }
}

Maintenant, à l'intérieur d'une classe différente C, la classe Best accessible sans créer d'instance de classe A.

public class C {
    A.B ab = new A.B();
}

staticles classes peuvent aussi avoir des non-staticmembres. Seule la classe devient statique.

Mais si le staticmot-clé est supprimé de la classe B, il n'est pas accessible directement sans créer une instance de A.

public class C {
    A a = new A();
    A.B ab = a. new B();
}

Mais nous ne pouvons pas avoir de staticmembres à l'intérieur d'une non-staticclasse intérieure.

Ramesh-X
la source
Pouvons-nous instancier une classe statique ou est-ce logique?
Supun Wijerathne
6
Pas comme dans d'autres langues, staticn'a qu'une seule signification en java. Si quelque chose est staticdans une classe, cela signifie que cette chose est accessible sans instancier cette classe. Il ne dit rien concernant la création d'instances ou non ..
Ramesh-X
Désolé stackoverflow! Je ne peux pas éviter de dire merci Ramesh-X dans ce cas! Vous avez couvert presque tout ce que je me demandais sur les classes internes statiques et les classes internes.
moldave
Vous ne pouvez pas "définir des classes internes comme statiques". C'est une contradiction dans les termes . Une classe imbriquée est interne ou statique.
Marquis de Lorne
13

Étant donné que c'est le meilleur résultat sur Google pour "java de classe statique" et que la meilleure réponse n'est pas ici, j'ai pensé que je l'ajouterais. J'interprète la question d'OP comme concernant les classes statiques en C #, qui sont connues sous le nom de singletons dans le monde Java. Pour ceux qui ne le savent pas, en C # le mot-clé "statique" peut être appliqué à une déclaration de classe ce qui signifie que la classe résultante ne peut jamais être instanciée.

Extrait de "Effective Java - Second Edition" de Joshua Bloch (largement considéré comme l'un des meilleurs guides de style Java disponibles):

Depuis la version 1.5, il existe une troisième approche pour implémenter les singletons. Créez simplement un type enum avec un élément:

// Enum singleton - the preferred approach
public enum Elvis {
    INSTANCE;
    public void leaveTheBuilding() { ... }
}

Cette approche est fonctionnellement équivalente à l'approche du domaine public, sauf qu'elle est plus concise, fournit gratuitement le mécanisme de sérialisation et fournit une garantie à toute épreuve contre les instanciations multiples, même face à des attaques sophistiquées de sérialisation ou de réflexion. Bien que cette approche n'ait pas encore été largement adoptée, un type d'énumération à un seul élément est le meilleur moyen d'implémenter un singleton. (souligné par l'auteur)

Bloch, Joshua (2008-05-08). Java efficace (série Java) (p. 18). Éducation Pearson.

Je pense que la mise en œuvre et la justification sont assez explicites.

Bennet Huber
la source
6
Un bon moyen d'implémenter un Singleton. Malheureusement, la question ne concerne pas les singletons, mais les classes statiques
David SN
1
Java a une interprétation assez unique du mot-clé "statique". Il semble que OP provienne de C # où "classe statique" est l'équivalent d'un singleton en Java. J'ai mis à jour ma réponse pour clarifier cette interprétation de la question.
Bennet Huber
1
La classe statique AC # n'est pas un singleton. Une instance Singleton est un objet et peut implémenter une interface, ce qui signifie qu'elle peut participer à l'injection de dépendances et peut être moquée. La classe statique AC # ne peut pas implémenter une interface ou être injectée de quelque façon que ce soit, et est beaucoup plus proche d'un tas de fonctions C, et bien sûr permet des méthodes d'extension.
Novaterata
13

Une classe peut-elle être statique en Java?

La réponse est OUI , nous pouvons avoir une classe statique en java. En java, nous avons des variables d'instance statiques ainsi que des méthodes statiques et également un bloc statique . Les classes peuvent également être rendues statiques en Java.

En java, nous ne pouvons pas rendre la classe de niveau supérieur (externe) statique. Seules les classes imbriquées peuvent être statiques.

classe imbriquée statique vs classe imbriquée non statique

1) La classe statique imbriquée n'a pas besoin d'une référence de classe externe, mais la classe imbriquée non statique ou la classe interne nécessite une référence de classe externe.

2) La classe interne (ou classe imbriquée non statique) peut accéder aux membres statiques et non statiques de la classe externe. Une classe statique ne peut pas accéder aux membres non statiques de la classe Outer. Il ne peut accéder qu'aux membres statiques de la classe Outer.

voir ici: https://docs.oracle.com/javase/tutorial/java/javaOO/nested.html

roottraveller
la source
les classes internes non statiques ne peuvent pas non plus déclarer de champs ou de méthodes statiques
Mr.Cat
8

Les classes externes ne peuvent pas être statiques, mais les classes imbriquées / internes peuvent l'être. Cela vous aide essentiellement à utiliser la classe imbriquée / interne sans créer d'instance de la classe externe.

Saket
la source
2

En termes simples, Java prend en charge la déclaration d'une classe comme étant statique uniquement pour les classes internes mais pas pour les classes de niveau supérieur.

classes de niveau supérieur: un projet java peut contenir plusieurs classes de niveau supérieur dans chaque fichier source java, l'une des classes étant nommée d'après le nom du fichier. Il n'y a que trois options ou mots-clés autorisés devant les classes de niveau supérieur, public, abstrait et final .

Classes internes : les classes qui se trouvent à l'intérieur d'une classe de niveau supérieur sont appelées classes internes, ce qui est essentiellement le concept de classes imbriquées. Les classes internes peuvent être statiques . L'idée de rendre les classes internes statiques, est de profiter de l'instanciation des objets des classes internes sans instancier l'objet de la classe de niveau supérieur. C'est exactement de la même manière que les méthodes et variables statiques fonctionnent à l'intérieur d'une classe de niveau supérieur.

Par conséquent, Java prend en charge les classes statiques au niveau de la classe interne (dans les classes imbriquées)

Et Java ne prend pas en charge les classes statiques aux classes de niveau supérieur.

J'espère que cela donne une solution plus simple à la question de la compréhension de base des classes statiques en Java.

saichand
la source
0

Java a des méthodes statiques qui sont associées aux classes (par exemple java.lang.Math n'a que des méthodes statiques), mais la classe elle-même n'est pas statique.

duffymo
la source
0

Vous ne pouvez pas utiliser le mot clé statique avec une classe sauf s'il s'agit d'une classe interne. Une classe interne statique est une classe imbriquée qui est un membre statique de la classe externe. Il est accessible sans instancier la classe externe, en utilisant d'autres membres statiques. Tout comme les membres statiques, une classe imbriquée statique n'a pas accès aux variables d'instance et aux méthodes de la classe externe.

public class Outer {
   static class Nested_Demo {
      public void my_method() {
          System.out.println("This is my nested class");
      }
   }
public static void main(String args[]) {
      Outer.Nested_Demo nested = new Outer.Nested_Demo();
      nested.my_method();
   }
}
Nahid Nisho
la source
Vous ne pouvez pas utiliser le staticmot - clé avec une classe sauf s'il s'agit d'une classe imbriquée . «Intérieur statique» est une contradiction dans les termes .
Marquis de Lorne
0

Une méthode statique signifie qu'elle est accessible sans créer d'objet de la classe, contrairement à public:

public class MyClass {
   // Static method
   static void myStaticMethod() {
      System.out.println("Static methods can be called without creating objects");
   }

  // Public method
  public void myPublicMethod() {
      System.out.println("Public methods must be called by creating objects");
   }

  // Main method
  public static void main(String[ ] args) {
      myStaticMethod(); // Call the static method
    // myPublicMethod(); This would output an error

    MyClass myObj = new MyClass(); // Create an object of MyClass
    myObj.myPublicMethod(); // Call the public method
  }
}
dJack
la source
Ne répond pas à la question.
Marquis de Lorne
-1

Toutes les bonnes réponses, mais je n'ai pas vu de référence à java.util.Collections qui utilise des tonnes de classe interne statique pour leurs méthodes de facteur statique. Donc, en ajoutant la même chose.

Ajout d'un exemple de java.util.Collections qui a plusieurs classes internes statiques. Les classes internes sont utiles pour regrouper le code qui doit être accessible via la classe externe.

/**
 * @serial include
 */
static class UnmodifiableSet<E> extends UnmodifiableCollection<E>
                             implements Set<E>, Serializable {
    private static final long serialVersionUID = -9215047833775013803L;

    UnmodifiableSet(Set<? extends E> s)     {super(s);}
    public boolean equals(Object o) {return o == this || c.equals(o);}
    public int hashCode()           {return c.hashCode();}
}

Voici la méthode du facteur statique dans la classe java.util.Collections

public static <T> Set<T> unmodifiableSet(Set<? extends T> s) {
    return new UnmodifiableSet<>(s);
}
Jay Rajput
la source
Vous n'avez pas obtenu votre commentaire? Peux-tu élaborer? Essayer de comprendre votre commentaire.
Jay Rajput