count
campo es estático en la Counter
clase, significa que puede hacer referencia a la variable con la siguiente expresión: Counter.count
. 
private
los campos están disponibles solo dentro de la clase en la que se declaran. Y protected
los campos están disponibles para todas las clases dentro de un paquete, así como para todas sus subclases fuera del paquete. Supongamos que la Counter
clase tiene un método estático increment()
cuyo trabajo es incrementar elcount
campo. Para llamar a este método, puede usar Counter.increment()
. No es necesario crear una instancia de la Counter
clase para acceder a un campo o método estático. Esta es la diferencia fundamental entre variables y métodos estáticos (clase) y variables y métodos NO estáticos (instancia). Una nota importante. No olvide que los miembros estáticos de la clase pertenecen directamente a la clase, no a ninguna instancia de la clase. Es decir, el valor de la count
variable estática será el mismo para todos Counter
los objetos. En este artículo, veremos los aspectos fundamentales del uso del modificador estático en Java, así como algunas características que lo ayudarán a comprender los conceptos clave de programación.
Lo que todo programador debe saber sobre el modificador estático en Java.
En esta sección, analizamos los aspectos principales del uso de métodos, campos y clases estáticos. Comencemos con las variables.-
NO PUEDE acceder a miembros no estáticos de una clase dentro de un contexto estático, como un método o bloque estático. Compilar el siguiente código dará como resultado un error:
public class Counter { private int count; public static void main(String args []) { System.out.println(count); // Compile time error } }
Este es uno de los errores más comunes que cometen los programadores de Java, especialmente los novatos. Dado que el
main
método es estático y lacount
variable no lo es, usar elprintln
método dentro delmain
método producirá un "error de tiempo de compilación". -
A diferencia de las variables locales, los campos y métodos estáticos NO están
thread safe
en Java. En la práctica, esta es una de las causas más frecuentes de problemas de seguridad en la programación multiproceso. Teniendo en cuenta que cada instancia de una clase hace referencia a la misma copia de una variable estática, dicha variable debe estar protegida o "bloqueada" por la clase. Por lo tanto, cuando use variables estáticas, asegúrese de que estén correctamentesynchronized
para evitar problemas comorace conditions
. -
Los métodos estáticos tienen la ventaja práctica de que no es necesario crear un nuevo objeto cada vez que desee llamarlos. Se puede llamar a un método estático usando el nombre de la clase que lo declara. Es por eso que estos métodos son perfectos para
factory
métodos yutility
métodos. Lajava.lang.Math
clase es un maravilloso ejemplo: casi todos sus métodos son estáticos. Las clases de utilidad de Java están marcadasfinal
por la misma razón. -
Otro punto importante es que no puede anular (
@Override
) métodos estáticos. Si declara un método de este tipo en unsubclass
, es decir, un método con el mismo nombre y firma, simplemente "oculta" el métodosuperclass
en lugar de anularlo. Este fenómeno se conoce comomethod hiding
. Esto significa que si se declara un método estático en las clases principal y secundaria, el método llamado siempre se basará en el tipo de variable en el momento de la compilación. A diferencia de la anulación de métodos, dichos métodos no se ejecutarán cuando se ejecute el programa. Consideremos un ejemplo:class Vehicle { public static void kmToMiles(int km) { System.out.println("Inside the parent class / static method"); } } class Car extends Vehicle { public static void kmToMiles(int km) { System.out.println("Inside the child class / static method"); } } public class Demo { public static void main(String args []) { Vehicle v = new Car(); v.kmToMiles(10); } }
Salida de la consola:
Dentro de la clase padre/método estático
El código demuestra claramente que, a pesar de que el objeto es un , se llama
Car
al método estático de la clase, ya que se llamó al método en tiempo de compilación.Vehicle
¡Y tenga en cuenta que no hubo errores de compilación! -
Además, además de las clases de nivel superior, puede declarar las clases estáticas. Tales clases se conocen como
nested static classes
. Son útiles para proporcionar una mejor cohesión. Un ejemplo llamativo de una clase estática anidada esHashMap.Entry
, que es una estructura de datos dentroHashMap
. Vale la pena señalar que, al igual que las clases internas, las clases anidadas estáticas se declaran en un archivo .class separado. Por lo tanto, si declara cinco clases anidadas en su clase principal, tendrá 6 archivos con la extensión .class. Otro ejemplo es la declaración propiaComparator
, como un comparador de edad (AgeComparator
) en laEmployee
clase. -
El modificador estático también se puede especificar en un bloque estático, más conocido como "bloque de inicialización estático", que se ejecuta cuando se carga la clase. Si no declara dicho bloque, Java recopila todos los campos estáticos en una sola lista y los inicializa cuando se carga la clase. Un bloque estático NO PUEDE arrojar excepciones marcadas, pero puede arrojar excepciones no marcadas. En este caso,
ExceptionInInitializerError
ocurrirá un. En la práctica, cualquier excepción que ocurra durante la inicialización de campos estáticos será envuelta en este error por Java. Esta es también la causa más común deNoClassDefFoundError
, porque la clase no estará en la memoria cuando se haga referencia a ella. -
Es útil saber que los métodos estáticos se vinculan en tiempo de compilación, a diferencia de los métodos virtuales o no estáticos, que se vinculan en tiempo de ejecución cuando se les llama en un objeto real. En consecuencia, los métodos estáticos no se pueden anular en Java, ya que el polimorfismo no se aplica a ellos en tiempo de ejecución. Esta es una limitación importante a tener en cuenta al declarar un método estático. Hacerlo tiene sentido solo cuando no hay capacidad o necesidad de anular el método en una subclase. Los métodos de fábrica y los métodos de utilidad son buenos ejemplos del uso adecuado del modificador estático. Joshua Bloch señala varias ventajas que los métodos de fábrica estáticos tienen sobre los constructores en su libro Java efectivo, que es una lectura obligatoria para todos los programadores de Java.
-
La inicialización es un aspecto importante de un bloque estático. Los campos estáticos o las variables se inicializan después de que la clase se carga en la memoria. El orden de inicialización es de arriba a abajo, en el mismo orden en que se declaran en el archivo fuente de la clase Java. Dado que los campos estáticos se inicializan de forma segura para subprocesos, este proceso también se utiliza para implementar el
Singleton
patrón. Si por alguna razón no está utilizando anEnum
como aSingleton
, entonces tiene una buena alternativa. Pero en este caso, debes tener en cuenta que no se trata de una inicialización "perezosa". Esto significa que el campo estático se inicializará incluso ANTES de que alguien "lo solicite". Si un objeto tiene muchos recursos o rara vez se usa, inicializarlo en un bloque estático no funcionará a su favor. -
Durante la serialización, los campos estáticos, como
transient
las variables, no se serializan. De hecho, si guarda datos en un campo estático, contendrá su valor inicial (predeterminado) después de la deserialización. Por ejemplo, si un campo estático es unint
, su valor será cero después de la deserialización. Si su tipo esfloat
, el valor será 0.0. Si el campo es unObject
, el valor seránull
. Para ser honesto, esta es una de las preguntas más frecuentes sobre serialización en entrevistas para puestos de Java. ¡No almacene datos de objetos esenciales en un campo estático! -
Finalmente, hablemos de la importación estática. Este modificador tiene mucho en común con la
import
instrucción estándar, pero se diferencia en que le permite importar uno o todos los miembros de la clase estática. Una vez que se importan los métodos estáticos, se puede acceder a ellos como si estuvieran declarados en la misma clase. De manera similar, al importar campos estáticos, podemos acceder a ellos sin especificar el nombre de la clase. Esta característica apareció en Java 1.5 y mejora la legibilidad del código cuando se usa correctamente. Esta construcción se encuentra con mayor frecuencia en las pruebas JUnit, ya que casi todos los desarrolladores de pruebas utilizan la importación estática para los métodos de aserción, por ejemplo,assertEquals()
y sus variantes sobrecargadas. -
Eso es todo por ahora. Todo programador de Java necesita conocer todos los aspectos del modificador estático mencionado anteriormente. Este artículo revisó información básica sobre variables estáticas, campos, métodos, bloques de inicialización e importaciones. También tocó algunas propiedades importantes que son esenciales para saber escribir y comprender programas Java. Espero que todos los desarrolladores perfeccionen su hábil uso de los miembros estáticos, porque es muy importante para el desarrollo de software serio".
GO TO FULL VERSION