Comment faire une copie de java.util.Liste dans un autre java.util.Liste
J'ai un List<SomeBean>
est rempli à partir d'un Service Web. Je veux copier/cloner le contenu de cette liste dans une liste vide du même type. Une recherche sur Google pour copier une liste m'a suggéré d'utiliser Collections.copy()
méthode. Dans tous les exemples que j'ai vu, la liste de destination était censé contenir le nombre exact d'éléments pour la copie de prendre place.
Que la liste que j'utilise est peuplée par l'intermédiaire d'un service web et il contient des centaines d'objets, je ne peux pas utiliser la technique ci-dessus. Ou je l'utilise mal??!! De toute façon, pour le faire fonctionner, j'ai essayé de faire quelque chose comme ça, mais j'ai encore un IndexOutOfBoundsException
.
List<SomeBean> wsList = app.allInOne(template);
List<SomeBean> wsListCopy=new ArrayList<SomeBean>(wsList.size());
Collections.copy(wsListCopy,wsList);
System.out.println(wsListCopy.size());
J'ai essayé d'utiliser le wsListCopy=wsList.subList(0, wsList.size())
, mais j'ai eu un ConcurrentAccessException
plus tard dans le code. Hit et du procès. 🙂
De toute façon, ma question est simple, comment puis-je copier le contenu de ma liste dans une autre Liste? Pas par itération, bien sûr.
- Toute copie sera l'utilisation de l'itération de cours. Vous pouvez le cacher, mais il sera toujours là.
- Tout d'abord: êtes-vous sûr que vous devez copier cette liste? Quelle est votre motivation à le faire?
- Yup, l'itération est juste caché sous des couches. Mais le commentaire a été ajouté pour éviter toute itération réponses. 🙂
- Je suis de l'exécution d'opérations sur la liste, comme removeAll(). Cela provoque la liste à la perte de ses données d'origine. Et "données" est également nécessaire par la suite.
- Quel est le type réel d'une liste, qui est de retour en
app.allInOne(template)
?ArrayList
? - Voulez-vous un copie superficielle ou profonde copie?
Vous devez vous connecter pour publier un commentaire.
Utiliser seulement ceci:
Remarque: toujours pas thread-safe, si vous modifiez
otherList
à partir d'un autre thread, alors vous pouvez faire queotherList
(et mêmenewList
) unCopyOnWriteArrayList
, par exemple, ou utiliser un verrou primitive, comme ReentrantReadWriteLock pour sérialiser les accès en lecture/écriture à ce que les listes sont simultanément accessibles.ConcurrentAccessException
.otherList
partir d'un autre thread (vous n'en avez pas, pensez-vous?)ArrayList
et vous voulez que la cible soit de la même mise en œuvre est la source ?List
ne devrait jamais être un sujet de préoccupation; si vous avez un problème de conception qui vous avez à résoudre en premier.C'est vraiment une bonne Java 8 façon de le faire:
Bien sûr, l'avantage ici est que vous pouvez filtrer et passer à la seule copie de la partie de la liste.
par exemple
list
est modifié alors que le collecteur est en cours d'exécution, unConcurrentModificationException
est levée..limit(list1.size() - 1)
Veuillez garder à l'esprit lors de l'utilisation de la addAll() méthode pour copier le contenu des deux le tableau des listes (originalArrayList et copyArrayofList) les références aux mêmes objets seront ajoutés à la liste si vous modifiez l'un d'eux puis copyArrayofList également reflètent aussi le même changement.
Si vous ne voulez pas d'effet secondaire, vous devrez copier chaque élément de la originalArrayList à la copyArrayofList, comme à l'aide d'une ou while.
Cela signifie que vous êtes en train de modifier la liste alors que vous essayez de le copier, le plus probable dans un autre thread. Pour corriger cela, vous devez soit
utiliser une collection qui est conçu pour l'accès simultané.
verrouiller la collection de manière appropriée de sorte que vous pouvez parcourir (ou vous permettent d'appeler une méthode qui fait cela pour vous)
trouver un écart pour éviter d'avoir à copier la liste d'origine.
Il existe une autre méthode avec Java 8 dans un null-sûre.
Si vous souhaitez ignorer un élément.
À partir de Java 10:
Liste.copyOf()
retourne un inmodifiableList
contenant les éléments de laCollection
.Le
Collection
ne doit pas êtrenull
, et il ne doit pas contenir denull
éléments.Aussi, si vous souhaitez créer une copie d'un
List
, vous pouvez trouver beaucoup de bonnes réponses ici.J'ai eu le même problème ConcurrentAccessException et mysolution était:
De sorte qu'il ne fonctionne qu'une seule opération à la fois et évite l'Exeption...
J'ai essayé quelque chose de similaire et a été en mesure de reproduire le problème (IndexOutOfBoundsException). Ci-dessous sont mes conclusions:
1) La mise en œuvre de la Collections.copier(destList, sourceList) vérifie d'abord la taille de la liste de destination par l'appel de la méthode size (). Depuis l'appel à la méthode size() retournera toujours le nombre d'éléments dans la liste (0 dans ce cas), le constructeur ArrayList(capacité) n'assure que la capacité initiale de la sauvegarde de tableau et cela n'a aucun rapport à la taille de la liste. Donc nous avons toujours obtenir IndexOutOfBoundsException.
2) Un moyen relativement simple est d'utiliser le constructeur qui prend une collection comme argument:
re:
indexOutOfBoundsException
, votre sous-liste les arguments sont le problème, vous devez mettre fin à la sous-liste à taille-1. Étant basé sur zéro, le dernier élément d'une liste est toujours de taille 1, il n'y a aucun élément dans la taille de la position, d'où l'erreur.Vous pouvez utiliser addAll().
par exemple :
wsListCopy.addAll(wsList);
Je ne vois aucune bonne réponse. Si vous voulez une copie en profondeur que vous avez à parcourir et copie de l'objet manuellement (vous pouvez utiliser un constructeur de copie).
Si vous ne voulez pas que les changements dans une liste à l'effet d'une autre liste de l'essayer.Il a travaillé pour moi
Espère que cette aide.
sous-fonction est un truc, l'objet retourné est toujours dans la liste d'origine.
ainsi, si vous effectuez aucune opération dans les sous-liste, il sera la cause de la simultanées exception dans votre code, peu importe, il est seul thread ou multi thread.