Comment supprimer tous les éléments nuls d'un tableau ArrayList ou String?

j'ai essayer avec une boucle comme ça

// ArrayList tourists

for (Tourist t : tourists) {
    if (t != null) {     
        t.setId(idForm); 
    }   
}

mais ce n'est pas gentil. Quelqu'un peut-il me proposer une meilleure solution?


Quelques repères pour faire la meilleure décision:

en boucle Pour boucle et Itérateur Test de Performance

161
demandé sur AZ_ 2011-01-27 20:21:07

16 réponses

, Essayez:

tourists.removeAll(Collections.singleton(null));

Lire API Java . Le code lancera java.lang.UnsupportedOperationException pour les listes immuables (telles que créées avec Arrays.asList ); voir cette réponse pour plus de détails.

331
répondu Lithium 2017-05-23 12:34:38

à partir de 2015, c'est la meilleure façon (Java 8):

tourists.removeIf(Objects::isNull);

Note: ce code lancera java.lang.UnsupportedOperationException pour les listes de taille fixe (telles que créées avec des tableaux.asList), y compris les listes immuables.

85
répondu MarcG 2016-12-19 14:21:06
list.removeAll(Collections.singleton(null));

Il Jette UnsupportedException si vous l'utilisez sur les Tableaux.asList parce qu'il vous donne immuable copie donc il ne peut pas être modifié. Voir ci-dessous le code. Il crée Mutable copie et ne lancera aucune exception.

public static String[] clean(final String[] v) {
    List<String> list = new ArrayList<String>(Arrays.asList(v));
    list.removeAll(Collections.singleton(null));
    return list.toArray(new String[list.size()]);
}
44
répondu AZ_ 2013-03-13 09:24:52

pas efficace, mais court

while(tourists.remove(null));
18
répondu Peter Lawrey 2011-01-27 17:25:26

si vous préférez les objets de données immuables, ou si vous ne voulez pas être destructeur de la liste d'entrées, vous pouvez utiliser les prédicats de Guava.

ImmutableList.copyOf(Iterables.filter(tourists, Predicates.notNull()))
17
répondu James Kojo 2012-07-30 19:54:16
 for (Iterator<Tourist> itr = tourists.iterator(); itr.hasNext();) {
      if (itr.next() == null) { itr.remove(); }
 }
7
répondu Mat Mannion 2011-01-27 17:23:38

il y a un moyen facile de supprimer toutes les valeurs null de collection .Vous devez passer une collection contenant null comme paramètre à removeAll() méthode

List s1=new ArrayList();
s1.add(null);

yourCollection.removeAll(s1);
3
répondu shiv 2011-11-15 09:35:19

la classe Objects a un nonNull Predicate qui peut être utilisé avec filter .

par exemple:

tourists.stream().filter(Objects::nonNull).collect(Collectors.toList());
3
répondu JeffF 2017-01-17 20:12:44

en utilisant Java 8, Vous pouvez le faire en utilisant stream() et filter()

tourists = tourists.stream().filter(t -> t != null).collect(Collectors.toList())

ou

tourists = tourists.stream().filter(Objects::nonNull).collect(Collectors.toList())

pour plus d'informations: Java 8-Streams

3
répondu Jad Chahine 2017-08-03 00:48:22

C'est un moyen facile de supprimer les valeurs nulles par défaut de arraylist

     tourists.removeAll(Arrays.asList(null));  

sinon chaîne valeur "null" Supprimer de arraylist

       tourists.removeAll(Arrays.asList("null"));  
2
répondu Jobin_vibes 2014-02-18 11:08:36

j'ai joué avec ça et j'ai découvert que trimToSize() semble fonctionner. Je travaille sur la plateforme Android donc ça pourrait être différent.

1
répondu theblitz 2011-05-19 10:00:53

nous pouvons utiliser iterator pour le même pour supprimer toutes les valeurs nulles.

Iterator<Tourist> itr= tourists.iterator();
while(itr.hasNext()){
    if(itr.next() == null){
        itr.remove();
    }
}
1
répondu amit 2015-07-23 11:31:17

j'ai utilisé l'interface stream ainsi que l'opération stream collect et une méthode helper-pour générer une nouvelle liste.

tourists.stream().filter(this::isNotNull).collect(Collectors.toList());

private <T> boolean isNotNull(final T item) {
    return  item != null;
}
1
répondu Mabi 2015-10-29 12:24:38

Pré-Java 8, vous devez utiliser:

tourists.removeAll(Collections.singleton(null));

Post-Java 8 use:

tourists.removeIf(Objects::isNull);

la raison en est la complexité temporelle. Le problème avec les tableaux est qu'une opération de suppression peut prendre du temps O(n) pour terminer. En fait, en Java, il s'agit d'une copie de tableau des éléments restants déplacés pour remplacer l'élément vide. De nombreuses autres solutions proposées ici déclencheront ce problème. Le premier est techniquement O(n*m) où m est 1 parce que c'est un singleton est nul: donc O(n)

vous devriez enlever tout le singleton, à l'intérieur il fait un batchRemove() qui a une position de lecture et une position d'écriture. Et parcourt la liste. Quand il frappe un null, il itère simplement la position de lecture par 1. Quand ils sont les mêmes il passe, quand ils sont différents il continue à se déplacer le long de la copie des valeurs. Puis à la fin il ajuste à la taille.

, Il a effectivement fait cela en interne:

public static <E> void removeNulls(ArrayList<E> list) {
    int size = list.size();
    int read = 0;
    int write = 0;
    for (; read < size; read++) {
        E element = list.get(read);
        if (element == null) continue;
        if (read != write) list.set(write, element);
        write++;
    }
    if (write != size) {
        list.subList(write, size).clear();
    }
}

que vous pouvez voir explicitement est une opération O(n).

la seule chose qui pourrait jamais être plus rapide est si vous itériez la liste des deux extrémités, et quand vous trouvez un null, vous définissez sa valeur égale à la valeur que vous avez trouvée à la fin, et décrémentez cette valeur. Et itérée jusqu'à ce que les deux valeurs correspondent. Vous gâcheriez l'ordre, mais réduirait considérablement le nombre de valeurs vous opposez ceux que vous avez laissés seuls. Ce qui est une bonne méthode pour savoir mais ne vous aidera pas beaucoup ici que .set() est fondamentalement libre, mais que le formulaire de suppression est un outil utile pour votre ceinture.


for (Iterator<Tourist> itr = tourists.iterator(); itr.hasNext();) {
      if (itr.next() == null) { itr.remove(); }
 }

bien que cela semble assez raisonnable, l' .supprimer () sur l'itérateur appels internes:

ArrayList.this.remove(lastRet);

qui est de nouveau l'opération O(n) dans le remove. Il ne fait pas de Système.arraycopy() qui n'est encore pas ce que vous voulez, si vous vous souciez de la vitesse. Cela fait n^2.

il y a aussi:

while(tourists.remove(null));

qui est O (M*N^2). Ici, nous ne nous contentons pas de répéter la liste. Nous réitérons la liste entière, chaque fois que nous correspondons à la nulle. Ensuite nous effectuons des opérations n/2 (moyennes) pour faire le système.arraycopy () pour effectuer la suppression. Vous pourriez littéralement, trier la collection entière entre les éléments avec des valeurs et des éléments avec des valeurs nulles et couper la fin en moins de temps. En fait, c'est vrai pour tous les cassés. Au moins en théorie, le système réel.arraycopy n'est pas vraiment un N fonctionnement dans la pratique. En théorie, la théorie et la pratique sont la même chose; en pratique, elles ne le sont pas.

1
répondu Tatarize 2017-05-28 03:21:40

utilisant Java 8 ceci peut être réalisé de différentes façons en utilisant des flux, des flux parallèles et la méthode removeIf :

List<String> stringList = new ArrayList<>(Arrays.asList(null, "A", "B", null, "C", null));
List<String> listWithoutNulls1 = stringList.stream()
                .filter(Objects::nonNull)
                .collect(Collectors.toList()); //[A,B,C]
List<String> listWithoutNulls2 = stringList.parallelStream()
                .filter(Objects::nonNull)
                .collect(Collectors.toList()); //[A,B,C]
stringList.removeIf(Objects::isNull); //[A,B,C]

le flux parallèle utilisera les processeurs disponibles et accélérera le processus pour les listes de taille raisonnable. Il est toujours conseillé de référence avant d'utiliser les ruisseaux.

0
répondu i_am_zero 2017-10-15 15:30:44

similaire à @Lithium answer mais ne jette pas de "liste ne peut pas contenir le type nul "erreur:

   list.removeAll(Collections.<T>singleton(null));
0
répondu Hannah Louisa Carney 2018-02-05 05:53:49