Ich versuche, einen temporären Container einer Klasse zu behalten, die Mitglied enthält:
HashMap<Integer,myObject> myobjectHashMap
Eine Klasse namens myobjectsList
Dann mach ich
myojbectsListA = new myojbectsList();
myojbectsListB = new myobjectsList();
dann: Füge einige Hashmap-Elemente zu A hinzu (like2)
dann
myobjectListB = myobjectListA; //B has 2
dann: Fügen Sie Hash-Map-Elemente zu A hinzu; (wie 4 weitere)
Geben Sie dann A zu den in B gespeicherten Elementen zurück.
myobjectListA = myobjectListb;
Aber wenn ich das mache, wächst B mit A, während ich A Hashmap-Elemente hinzufüge. A enthält jetzt 6 Elemente, weil B 6 hatte.
Ich möchte, dass A Original 2 nach der letzten Bewertung in C ++ noch am Ende hat. Ich würde Kopie mit Objekten verwenden. Was ist das Java-Äquivalent?
Hinzugefügt: OK Ich habe etwas ausgelassen, um dies zu erklären. MyObjectsList enthält keine HashMap, sondern leitet sich von einer Klasse MyBaseOjbectsList ab, die das HashMap-Mitglied hat, und MyObjectsList erweitert MyBaseOjbectsList. Macht das einen Unterschied?
Antworten:
Wenn Sie eine Kopie der HashMap möchten, müssen Sie eine neue mit erstellen.
Dadurch wird eine (flache) Kopie der Karte erstellt.
quelle
myObjectListB.addAll(myObjectListA)
addAll
ist fürHashSet
.putAll
ist fürHashMap
.Sie können auch verwenden
Methode zum Kopieren aller Elemente von einer Hashmap in eine andere Hashmap
Programm zum Kopieren aller Elemente von einer Hashmap in eine andere
Quelle: http://www.tutorialdata.com/examples/java/collection-framework/hashmap/copy-all-elements-from-one-hashmap-to-another
quelle
HashMap
undputAll
alles darin. Es ist völlig sinnlos.Der Unterschied besteht darin, dass sich Ihr Objekt in C ++ auf dem Stapel befindet, während sich Ihr Objekt in Java auf dem Heap befindet. Wenn A und B Objekte sind, können Sie in Java jederzeit Folgendes tun:
A und B zeigen auf dasselbe Objekt, also tun Sie alles, was Sie A antun, B und umgekehrt.
Verwenden Sie new,
HashMap()
wenn Sie zwei verschiedene Objekte möchten.Und Sie können
Map.putAll(...)
damit Daten zwischen zwei Karten kopieren.quelle
Hier gibt es eine kleine (RIESIGE) Untertreibung. Wenn Sie ein Objekt
HashMap
mit verschachtelten StrukturenHashMap.putAll()
kopieren möchten , wird es als Referenz kopiert, da es nicht genau weiß, wie Ihr Objekt kopiert werden soll. Beispielsweise:Grundsätzlich müssen Sie die Felder wie hier selbst kopieren
quelle
Wenn Sie in Java schreiben:
objectA
undobjectB
sind gleich und verweisen auf die gleiche Referenz. Wenn Sie eines ändern, wird das andere geändert. Wenn Sie also den Status vonobjectA
(nicht dessen Referenz)objectB
ändern, wird diese Änderung ebenfalls berücksichtigt.Wenn Sie jedoch schreiben:
Zeigt dann
objectB
immer noch auf das erste Objekt, das Sie erstellt haben (OriginalobjectA
), währendobjectA
es jetzt auf ein neues Objekt zeigt.quelle
Wenn wir ein Objekt in Java kopieren möchten, müssen wir zwei Möglichkeiten berücksichtigen: eine flache Kopie und eine tiefe Kopie .
Die flache Kopie ist der Ansatz, wenn wir nur Feldwerte kopieren. Daher kann die Kopie vom Originalobjekt abhängig sein. Beim Deep Copy- Ansatz stellen wir sicher, dass alle Objekte im Baum tief kopiert werden, sodass die Kopie nicht von einem früheren vorhandenen Objekt abhängig ist, das sich jemals ändern könnte.
Diese Frage ist die perfekte Definition für die Anwendung des Deep-Copy- Ansatzes.
Wenn Sie eine einfache
HashMap<Integer, List<T>>
Karte haben, erstellen wir zunächst eine solche Problemumgehung. Erstellen einer neuen Instanz desList<T>
.Dieser verwendet eine
Stream.collect()
Methode zum Erstellen der Klonzuordnung, verwendet jedoch dieselbe Idee wie die vorherige Methode.Wenn die darin enthaltenen Instanzen
T
jedoch auch veränderbare Objekte sind , haben wir ein großes Problem. In diesem Fall ist eine wirklich tiefe Kopie eine Alternative, die dieses Problem löst. Sein Vorteil ist, dass mindestens jedes veränderbare Objekt im Objektgraphen rekursiv kopiert wird. Da die Kopie nicht von einem zuvor erstellten veränderlichen Objekt abhängig ist , wird sie nicht versehentlich geändert, wie wir es bei der flachen Kopie gesehen haben.Um das zu lösen, werden diese Deep Copy-Implementierungen die Arbeit erledigen.
quelle
Seit Java 10 ist es möglich zu verwenden
zum Erstellen einer flachen Kopie , die ebenfalls unveränderlich ist. (Hier ist seine Javadoc ). Wie in dieser Antwort erwähnt , benötigen Sie für eine tiefe Kopie eine Art Wertzuordnung, um eine sichere Kopie der Werte zu erstellen. Sie müssen jedoch keine Schlüssel kopieren , da diese unveränderlich sein müssen .
quelle
Da diese Frage immer noch unbeantwortet ist und ich ein ähnliches Problem hatte, werde ich versuchen, dies zu beantworten. Das Problem (wie bereits erwähnt) besteht darin, dass Sie nur Verweise auf dasselbe Objekt kopieren und daher durch eine Änderung an der Kopie auch das Ursprungsobjekt geändert wird. Sie müssen also das Objekt (Ihren Kartenwert) selbst kopieren. Der einfachste Weg, dies zu tun, besteht darin, alle Ihre Objekte so zu gestalten, dass sie die serialisierbare Schnittstelle implementieren. Serialisieren und deserialisieren Sie dann Ihre Karte, um eine echte Kopie zu erhalten. Sie können dies selbst tun oder die Apache Commons SerializationUtils # clone () verwenden, die Sie hier finden: https://commons.apache.org/proper/commons-lang/javadocs/api-2.6/org/apache/commons/ lang / SerializationUtils.html Beachten Sie jedoch, dass dies der einfachste Ansatz ist, es jedoch eine teure Aufgabe ist, viele Objekte zu serialisieren und zu deserialisieren.
quelle
Wenn Sie ein Objekt einem anderen zuweisen, kopieren Sie lediglich den Verweis auf das Objekt und nicht den Inhalt. Sie müssen lediglich Ihr Objekt B nehmen und den Inhalt von Objekt A manuell kopieren.
Wenn Sie dies häufig tun, können Sie eine
clone()
Methode für die Klasse implementieren , mit der ein neues Objekt desselben Typs erstellt und der gesamte Inhalt in das neue Objekt kopiert wird.quelle
Da das OP erwähnt hat, dass er keinen Zugriff auf die Basisklasse hat, in der sich eine HashMap befindet - ich fürchte, es sind nur sehr wenige Optionen verfügbar.
Eine (schmerzhaft langsame und ressourcenintensive) Möglichkeit, eine tiefe Kopie eines Objekts in Java auszuführen, besteht darin, die "serialisierbare" Schnittstelle zu missbrauchen, die viele Klassen absichtlich oder unbeabsichtigt erweitern, und diese dann zu verwenden, um Ihre Klasse in ByteStream zu serialisieren. Nach der De-Serialisierung erhalten Sie eine tiefe Kopie des betreffenden Objekts.
Eine Anleitung dazu finden Sie hier: https://www.avajava.com/tutorials/lessons/how-do-i-perform-a-deep-clone-using-serializable.html
quelle