Tipos de anotación de Java
Tipos de anotaciones de Java
En este tutorial, aprenderemos sobre diferentes tipos de anotaciones de Java con la ayuda de ejemplos.
Las anotaciones de Java son metadatos (datos sobre datos) para el código fuente de nuestro programa. Hay varias anotaciones predefinidas proporcionadas por Java SE. Además, también podemos crear anotaciones personalizadas según nuestras necesidades.
Si no sabe qué son las anotaciones, visite el tutorial de anotaciones de Java.
Estas anotaciones se pueden categorizar como:
1. Anotaciones predefinidas
@Deprecated
@Override
@SuppressWarnings
@SafeVarargs
@FunctionalInterface
2. Anotaciones personalizadas
3. Meta-anotaciones
@Retention
@Documented
@Target
@Inherited
@Repeatable
Tipos de anotación predefinidos
1. @Obsoleto
El @Deprecated
anotación es una anotación de marcador que indica que el elemento (clase, método, campo, etc.) está en desuso y ha sido reemplazado por un elemento más nuevo.
Su sintaxis es:
@Deprecated
accessModifier returnType deprecatedMethodName() { ... }
Cuando un programa usa el elemento que ha sido declarado obsoleto, el compilador genera una advertencia.
Usamos Javadoc @deprecated
etiqueta para documentar el elemento en desuso.
/**
* @deprecated
* why it was deprecated
*/
@Deprecated
accessModifier returnType deprecatedMethodName() { ... }
Ejemplo 1:@Ejemplo de anotación en desuso
class Main {
/**
* @deprecated
* This method is deprecated and has been replaced by newMethod()
*/
@Deprecated
public static void deprecatedMethod() {
System.out.println("Deprecated method");
}
public static void main(String args[]) {
deprecatedMethod();
}
}
Salida
Deprecated method
2. @Anular
El @Override
La anotación especifica que un método de una subclase anula el método de la superclase con el mismo nombre de método, tipo de devolución y lista de parámetros.
No es obligatorio usar @Override
al anular un método. Sin embargo, si lo usamos, el compilador da un error si algo está mal (como un tipo de parámetro incorrecto) mientras anula el método.
Ejemplo 2:ejemplo de anotación @Override
class Animal {
// overridden method
public void display(){
System.out.println("I am an animal");
}
}
class Dog extends Animal {
// overriding method
@Override
public void display(){
System.out.println("I am a dog");
}
public void printMessage(){
display();
}
}
class Main {
public static void main(String[] args) {
Dog dog1 = new Dog();
dog1.printMessage();
}
}
Salida
I am a dog
En este ejemplo, al hacer un objeto dog1 de Perro class, podemos llamar a su método printMessage() que luego ejecuta el display()
declaración.
Desde display()
está definido en ambas clases, el método de la subclase Dog anula el método de la superclase Animal . Por lo tanto, el display()
de la subclase se llama.
3. @Suprimir advertencias
Como sugiere el nombre, el @SuppressWarnings
La anotación indica al compilador que suprima las advertencias que se generan mientras se ejecuta el programa.
Podemos especificar el tipo de advertencias a suprimir. Las advertencias que se pueden suprimir son específicas del compilador, pero hay dos categorías de advertencias:desaprobación y sin marcar .
Para suprimir una categoría particular de advertencia, usamos:
@SuppressWarnings("warningCategory")
Por ejemplo,
@SuppressWarnings("deprecated")
Para suprimir varias categorías de advertencias, usamos:
@SuppressWarnings({"warningCategory1", "warningCategory2"})
Por ejemplo,
@SuppressWarnings({"deprecated", "unchecked"})
Categoría deprecated
indica al compilador que suprima las advertencias cuando usamos un elemento obsoleto.
Categoría unchecked
indica al compilador que suprima las advertencias cuando usamos tipos sin formato.
Y las advertencias no definidas se ignoran. Por ejemplo,
@SuppressWarnings("someundefinedwarning")
Ejemplo 3:ejemplo de anotación @SuppressWarnings
class Main {
@Deprecated
public static void deprecatedMethod() {
System.out.println("Deprecated method");
}
@SuppressWarnings("deprecated")
public static void main(String args[]) {
Main depObj = new Main();
depObj. deprecatedMethod();
}
}
Salida
Deprecated method
Aquí, deprecatedMethod()
se ha marcado como obsoleto y dará advertencias al compilador cuando se use. Usando el @SuppressWarnings("deprecated")
anotación, podemos evitar las advertencias del compilador.
4. @SafeVarargs
El @SafeVarargs
anotación afirma que el método o constructor anotado no realiza operaciones no seguras en sus varargs (número variable de argumentos).
Solo podemos usar esta anotación en métodos o constructores que no se pueden anular. Esto se debe a que los métodos que los anulan pueden realizar operaciones no seguras.
Antes de Java 9, podíamos usar esta anotación solo en métodos estáticos o finales porque no se pueden anular. Ahora también podemos usar esta anotación para métodos privados.
Ejemplo 4:ejemplo de anotación @SafeVarargs
import java.util.*;
class Main {
private void displayList(List<String>... lists) {
for (List<String> list : lists) {
System.out.println(list);
}
}
public static void main(String args[]) {
Main obj = new Main();
List<String> universityList = Arrays.asList("Tribhuvan University", "Kathmandu University");
obj.displayList(universityList);
List<String> programmingLanguages = Arrays.asList("Java", "C");
obj.displayList(universityList, programmingLanguages);
}
}
Advertencias
Type safety: Potential heap pollution via varargs parameter lists Type safety: A generic array of List<String> is created for a varargs parameter
Salida
Note: Main.java uses unchecked or unsafe operations. [Tribhuvan University, Kathmandu University] [Tribhuvan University, Kathmandu University] [Java, C]
Aquí, List
... lists
especifica un argumento de longitud variable de tipo List
. Esto significa que el método displayList()
puede tener cero o más argumentos.
El programa anterior compila sin errores pero da advertencias cuando @SafeVarargs
no se utiliza la anotación.
Cuando usamos @SafeVarargs
anotación en el ejemplo anterior,
@SafeVarargs private void displayList(List<String>... lists) { ... }
Obtenemos el mismo resultado pero sin ninguna advertencia. Las advertencias no marcadas también se suprimen cuando usamos esta anotación.
5. @InterfazFuncional
Java 8 presentó por primera vez este @FunctionalInterface
anotación. Esta anotación indica que la declaración de tipo en la que se utiliza es una interfaz funcional. Una interfaz funcional solo puede tener un método abstracto.
Ejemplo 5:ejemplo de anotación @FunctionalInterface
@FunctionalInterface
public interface MyFuncInterface{
public void firstMethod(); // this is an abstract method
}
Si agregamos otro método abstracto, digamos
@FunctionalInterface
public interface MyFuncInterface{
public void firstMethod(); // this is an abstract method
public void secondMethod(); // this throws compile error
}
Ahora, cuando ejecutemos el programa, obtendremos la siguiente advertencia:
Unexpected @FunctionalInterface annotation @FunctionalInterface ^ MyFuncInterface is not a functional interface multiple non-overriding abstract methods found in interface MyFuncInterface
No es obligatorio usar @FunctionalInterface
anotación. El compilador considerará cualquier interfaz que cumpla con la definición de interfaz funcional como una interfaz funcional.
Usamos esta anotación para asegurarnos de que la interfaz funcional tenga solo un método abstracto.
Sin embargo, puede tener cualquier cantidad de métodos predeterminados y estáticos porque tienen una implementación.
@FunctionalInterface
public interface MyFuncInterface{
public void firstMethod(); // this is an abstract method
default void secondMethod() { ... }
default void thirdMethod() { ... }
}
Anotaciones personalizadas
También es posible crear nuestras propias anotaciones personalizadas.
Su sintaxis es:
[Access Specifier] @interface<AnnotationName> { DataType <Method Name>() [default value]; }
Esto es lo que necesita saber sobre la anotación personalizada:
- Las anotaciones se pueden crear usando
@interface
seguido del nombre de la anotación. - La anotación puede tener elementos que parecen métodos pero no tienen una implementación.
- El valor predeterminado es opcional. Los parámetros no pueden tener un valor nulo.
- El tipo de retorno del método puede ser primitivo, enumeración, cadena, nombre de clase o matriz de estos tipos.
Ejemplo 6:Ejemplo de anotación personalizada
@interface MyCustomAnnotation {
String value() default "default value";
}
class Main {
@MyCustomAnnotation(value = "programiz")
public void method1() {
System.out.println("Test method 1");
}
public static void main(String[] args) throws Exception {
Main obj = new Main();
obj.method1();
}
}
Salida
Test method 1
Metanotaciones
Las meta-anotaciones son anotaciones que se aplican a otras anotaciones.
1. @Retención
El @Retention
anotación especifica el nivel hasta el cual la anotación estará disponible.
Su sintaxis es:
@Retention(RetentionPolicy)
Hay 3 tipos de políticas de retención:
- RetentionPolicy.SOURCE - La anotación está disponible solo en el nivel de fuente y el compilador la ignora.
- RetentionPolicy.CLASS - La anotación está disponible para el compilador en tiempo de compilación, pero la máquina virtual de Java (JVM) la ignora.
- RetentionPolicy.RUNTIME - La anotación está disponible para la JVM.
Por ejemplo,
@Retention(RetentionPolicy.RUNTIME)
public @interface MyCustomAnnotation{ ... }
2. @Documentado
De forma predeterminada, las anotaciones personalizadas no se incluyen en la documentación oficial de Java. Para incluir nuestra anotación en la documentación de Javadoc, usamos el @Documented
anotación.
Por ejemplo,
@Documented
public @interface MyCustomAnnotation{ ... }
3. @Objetivo
Podemos restringir una anotación para que se aplique a objetivos específicos usando el @Target
anotación.
Su sintaxis es:
@Target(ElementType)
El ElementType
puede tener uno de los siguientes tipos:
Tipo de elemento | Objetivo |
---|---|
ElementType.ANNOTATION_TYPE | Tipo de anotación |
ElementType.CONSTRUCTOR | Constructores |
ElementType.FIELD | Campos |
ElementType.LOCAL_VARIABLE | Variables locales |
ElementType.METHOD | Métodos |
ElementType.PACKAGE | Paquete |
ElementType.PARAMETER | Parámetro |
ElementType.TYPE | Cualquier elemento de clase |
Por ejemplo,
@Target(ElementType.METHOD)
public @interface MyCustomAnnotation{ ... }
En este ejemplo, hemos restringido el uso de esta anotación solo a los métodos.
4. @Heredado
De forma predeterminada, un tipo de anotación no se puede heredar de una superclase. Sin embargo, si necesitamos heredar una anotación de una superclase a una subclase, usamos el @Inherited
anotación.
Su sintaxis es:
@Inherited
Por ejemplo,
@Inherited
public @interface MyCustomAnnotation { ... }
@MyCustomAnnotation
public class ParentClass{ ... }
public class ChildClass extends ParentClass { ... }
5. @Repetible
Una anotación que ha sido marcada por @Repeatable
se puede aplicar varias veces a la misma declaración.
@Repeatable(Universities.class)
public @interface University {
String name();
}
El valor definido en el @Repeatable
anotación es la anotación del contenedor. La anotación del contenedor tiene una variable valor del tipo de matriz de la anotación repetible anterior. Aquí, Universities
son el tipo de anotación contenedora.
public @interface Universities {
University[] value();
}
Ahora, el @University
la anotación se puede utilizar varias veces en la misma declaración.
@University(name = "TU")
@University(name = "KU")
private String uniName;
Si necesitamos recuperar los datos de la anotación, podemos usar la API de Reflection.
Para recuperar valores de anotación, usamos getAnnotationsByType()
o getAnnotations()
método definido en la API de Reflection.
Java
- Tipos de datos Java (primitivos)
- Operadores Java
- Interfaz Java
- Prueba de Java con recursos
- Anotaciones Java
- Tipos de anotación de Java
- Método Java String charAt() con ejemplo
- Java String termina con () método con ejemplo
- Método Java String replace(), replaceAll() y replaceFirst()
- Java - Tipos de variables
- Java - Tipos de modificadores