Question

Parfois, quand on regarde par le code, je vois de nombreuses méthodes spécifient une annotation:

@SuppressWarnings("unchecked")

Qu'est-ce que cela signifie?

Était-ce utile?

La solution

Parfois, Java génériques juste ne vous laissez pas faire ce que vous voulez, et vous avez besoin de dire efficacement le compilateur que ce que vous faites vraiment légal au moment de l'exécution.

Je trouve habituellement ce une douleur quand je suis moqueur une interface générique, mais il y a d'autres exemples aussi. Il est généralement intéressant d'essayer de trouver un moyen d'éviter la mise en garde plutôt que de le supprimer ( Java Generics FAQ aide ici), mais parfois même si elle est possible, il plie le code de la forme tant que la suppression de l'avertissement est plus propre. Toujours ajouter un commentaire explicatif dans ce cas!

Le même génériques FAQ a plusieurs sections sur ce sujet, à commencer par "Qu'est-ce que un avertissement « sans contrôle » " -. il vaut bien une lecture

Autres conseils

Il est une annotation pour supprimer compiler des avertissements sur les opérations génériques non vérifiées (pas d'exceptions), telles que des moulages. Elle implique essentiellement que le programmeur ne voulait pas être informé au sujet de ces qu'il est déjà au courant lors de la compilation un peu de code particulier.

Vous pouvez en savoir plus sur cette annotation spécifique ici:

  

SuppressWarnings

En outre, Oracle fournit une documentation tutoriel sur l'utilisation des annotations ici:

  

Annotations

Comme ils disent,

  

« L'avertissement « sans contrôle » peut se produire lorsque l'interface avec le code existant écrit avant l'arrivée des génériques (discuté dans la leçon intitulée Generics). »

Il pourrait également signifier que la version actuelle du système de type Java est pas assez bon pour votre cas. Il y avait plusieurs Propositions JSR / hacks pour fixer ceci: jetons de type, super type Tokens , Class.cast ().

Si vous avez vraiment besoin de cette supression, affinez autant que possible (par exemple ne pas le mettre sur la classe elle-même ou sur une méthode longue). Un exemple:

public List<String> getALegacyListReversed() {
   @SuppressWarnings("unchecked") List<String> list =
       (List<String>)legacyLibrary.getStringList();

   Collections.reverse(list);
   return list;
}

Le SuppressWarning annotation utilisé pour supprimer les avertissements de compilation pour l'élément annoté. Plus précisément, la catégorie unchecked permet la suppression des avertissements du compilateur généré en raison du type non contrôlée jette.

Il suffit de:. Il est un avertissement par lequel le compilateur indique qu'il ne peut pas assurer la sécurité de type

méthode de service JPA par exemple:

@SuppressWarnings("unchecked")
public List<User> findAllUsers(){
    Query query = entitymanager.createQuery("SELECT u FROM User u");
    return (List<User>)query.getResultList();
}

Si je didn'n anotate les @SuppressWarnings ( « non contrôlée ») ici, il aurait un problème avec la ligne, où je veux retourner mon de résultats.

type sécurité raccourci signifie:. Un programme est considéré comme le type de sécurité si elle compile sans erreurs et les avertissements et ne soulève pas de ClassCastException inattendu s lors de l'exécution

Je construis sur http://www.angelikalanger.com/GenericsFAQ/FAQSections/Fundamentals .html

En Java, les médicaments génériques sont mis en œuvre au moyen d'un effacement de type. Par exemple, le code suivant.

List<String> hello = List.of("a", "b");
String example = hello.get(0);

est compilé à ce qui suit.

List hello = List.of("a", "b");
String example = (String) hello.get(0);

est défini comme List.of.

static <E> List<E> of(E e1, E e2);

qui, après l'effacement de type devient.

static List of(Object e1, Object e2);

Le compilateur n'a aucune idée de ce que sont des types génériques à l'exécution, donc si vous écrivez quelque chose comme ça.

Object list = List.of("a", "b");
List<Integer> actualList = (List<Integer>) list;

Java Virtual Machine n'a aucune idée de ce que les types génériques sont en cours d'exécution d'un programme, cette compile et fonctionne, comme pour la machine virtuelle Java, c'est un casting type List (ce qui est la seule chose qu'il peut vérifier, il vérifie seulement).

Mais ajoutez cette ligne.

Integer hello = actualList.get(0);

Et JVM va jeter un ClassCastException inattendu, comme compilateur Java inséré un casting implicite.

java.lang.ClassCastException: java.base/java.lang.String cannot be cast to java.base/java.lang.Integer

Un avertissement unchecked indique un programmeur qu'un casting peut provoquer un programme pour lancer une exception quelque part ailleurs. L'avertissement avec suppression @SuppressWarnings("unchecked") indique au compilateur que le programmeur croit que le code pour être sûr et ne causera pas des exceptions inattendues.

Pourquoi voudriez-vous faire cela? système de type Java est pas assez bon pour représenter tous les modèles d'utilisation de type possibles. Parfois, vous savez peut-être qu'un casting est sûr, mais Java ne fournit pas un moyen de le dire - pour cacher les avertissements comme celui-ci, @SupressWarnings("unchecked") peut être utilisé, de sorte qu'un programmeur peut se concentrer sur les avertissements réels. Par exemple, Optional.empty() retourne un singleton pour éviter l'attribution de optionals vides qui ne stocke pas une valeur.

private static final Optional<?> EMPTY = new Optional<>();
public static<T> Optional<T> empty() {
    @SuppressWarnings("unchecked")
    Optional<T> t = (Optional<T>) EMPTY;
    return t;
}

Cette fonte est sûr, que la valeur stockée dans un vide en option ne peut pas être récupéré donc il n'y a pas de risque d'exceptions de la distribution des classes inattendues.

Vous pouvez supprimer les avertissements du compilateur et de dire les génériques que le code que vous aviez écrit est légal selon elle.

Exemple:

@SuppressWarnings("unchecked")
public List<ReservationMealPlan> retreiveMealPlan() {
     List<ReservationMealPlan> list=new ArrayList<ReservationMealPlan>();
    TestMenuService testMenuService=new TestMenuService(em, this.selectedInstance);
    list = testMenuService.getMeal(reservationMealPlan);
    return list;
 }

Une astuce consiste à créer une interface qui étend une interface de base générique ...

public interface LoadFutures extends Map<UUID, Future<LoadResult>> {}

Ensuite, vous pouvez le vérifier avec instanceof avant la distribution ...

Object obj = context.getAttribute(FUTURES);
if (!(obj instanceof LoadFutures)) {
    String format = "Servlet context attribute \"%s\" is not of type "
            + "LoadFutures. Its type is %s.";
    String msg = String.format(format, FUTURES, obj.getClass());
    throw new RuntimeException(msg);
}
return (LoadFutures) obj;

En ce qui concerne je sais, pour l'instant, il doit faire avec la suppression des avertissements sur les médicaments génériques; génériques sont une nouvelle construction de programmation non pris en charge dans les versions antérieures de JDK 5 JDK, donc des mélanges des vieilles constructions avec les nouvelles pourraient poser des résultats inattendus.

Le compilateur avertit le programmeur à ce sujet, mais si le programmeur connaît déjà, ils peuvent transformer ces avertissements redoutés de l'aide SuppressWarnings.

Un avertissement par lequel le compilateur indique qu'il ne peut pas assurer la sécurité de type. Le terme avertissement « sans contrôle » est trompeur. Cela ne signifie pas que l'avertissement est sans contrôle d'aucune façon. Le terme « sans contrôle » fait référence au fait que le compilateur et le système d'exécution ne sont pas suffisamment d'informations de type pour effectuer tous les contrôles de type qui seraient nécessaires pour assurer la sécurité de type. En ce sens, certaines opérations sont « sans contrôle ».

La source la plus courante d'avertissements « non vérifiées » est l'utilisation de types bruts. avertissements « non vérifiées » sont émis lorsqu'un objet est accessible par une variable de type cru, parce que le type brut ne fournit pas suffisamment d'informations de type pour effectuer tous les contrôles de type nécessaires.

Exemple (d'avertissement sans contrôle, en liaison avec les types de base):

TreeSet set = new TreeSet(); 
set.add("abc");        // unchecked warning 
set.remove("abc");
warning: [unchecked] unchecked call to add(E) as a member of the raw type java.util.TreeSet 
               set.add("abc");  
                      ^

Lorsque la méthode d'ajout est appelé le compilateur ne sait pas s'il est sûr d'ajouter un objet String à la collection. Si le TreeSet est une collection qui contient la chaîne s (ou un super-type de celui-ci), il serait en sécurité. Mais à partir des informations de type fourni par le type brut TreeSet le compilateur ne peut pas dire. D'où l'appel est potentiellement dangereux et un avertissement « non contrôlée » est émise.

avertissements « non contrôlées » sont également rapportés lorsque le compilateur trouve une fonte dont le type de cible est soit un type paramétré ou un paramètre de type.

Exemple (d'un avertissement sans contrôle, en liaison avec une distribution à un type paramétré ou variable type):

  class Wrapper<T> { 
  private T wrapped ; 
  public Wrapper (T arg) {wrapped = arg;} 
  ... 
  public Wrapper <T> clone() { 
    Wrapper<T> clon = null; 
     try {  
       clon = (Wrapper<T>) super.clone(); // unchecked warning 
     } catch (CloneNotSupportedException e) {  
       throw new InternalError();  
     } 
     try {  
       Class<?> clzz = this.wrapped.getClass(); 
       Method   meth = clzz.getMethod("clone", new Class[0]); 
       Object   dupl = meth.invoke(this.wrapped, new Object[0]); 
       clon.wrapped = (T) dupl; // unchecked warning 
     } catch (Exception e) {} 
     return clon; 
  } 
} 
warning: [unchecked] unchecked cast 
found   : java.lang.Object 
required: Wrapper <T> 
                  clon = ( Wrapper <T>)super.clone();  
                                                ^ 
warning: [unchecked] unchecked cast 
found   : java.lang.Object 
required: T 
                  clon. wrapped = (T)dupl;

A coulé dont le type de cible est soit un type paramétré ou un paramètre de type (wildcard béton ou bornée) est dangereuse, si une vérification de type dynamique lors de l'exécution est impliqué. Lors de l'exécution, seul l'effacement de type est disponible, pas le type exact statique qui est visible dans le code source. En conséquence, la partie d'exécution de la distribution est effectuée sur la base de l'effacement de type, non pas sur le type statique exact.

Dans l'exemple, la distribution à Wrapper vérifierait si l'objet est revenu de super.clone est un wrapper, pas si elle est une enveloppe avec un type particulier de membres. De même, les moulages au paramètre de type T sont casté en type objet lors de l'exécution, et probablement optimisés loin tout à fait. En raison de l'effacement de type, le système d'exécution ne parvient pas à effectuer des contrôles de type plus utiles à l'exécution.

D'une certaine manière, le code source est trompeuse, car elle suggère qu'une fonte du type cible respective est réalisée, alors qu'en fait la partie dynamique de la distribution ne vérifie contre l'effacement de type de type cible. L'avertissement « sans contrôle » est émise pour attirer l'attention du programmeur à ce décalage entre l'aspect statique et dynamique de la distribution.

S'il vous plaît se référer: Qu'est-ce qu'un "non contrôlée"?

annotation @SuppressWarnings est l'une des trois annotations intégrées disponibles dans JDK et ajouté aux côtés @Override et @deprecated en Java 1.5.

@SuppressWarnings charger le compilateur d'ignorer ou de supprimer, avertissement du compilateur spécifié dans l'élément annoté et tous les éléments de programme à l'intérieur de cet élément. Par exemple, si une classe est annotée pour supprimer un avertissement particulier, alors un avertissement généré dans un procédé à l'intérieur de cette classe est également séparé.

Vous pourriez avoir vu @SuppressWarnings ( « sans contrôle ») et @SuppressWarnings ( « série »), deux exemples d'annotation @SuppressWarnings les plus populaires. L'ancien est utilisé pour supprimer l'avertissement généré en raison de la coulée sans contrôle alors que la mise en garde plus tard est utilisé pour rappeler l'ajout serialVersionUID dans une classe Serializable.

En savoir plus: https://javarevisited.blogspot.com/2015/09/what-is-suppresswarnings-annotation-in-java-unchecked-raw-serial.html#ixzz5rqQaOLUa

Licencié sous: CC-BY-SA avec attribution
Non affilié à StackOverflow
scroll top