# ECS: "deep copy" einer Entity-Vorlage



## Schmetterhand (4. Jan 2017)

Grüß Euch,

bin gerade dabei, ein kleines Spiel mit einem "Entity-Component-System" (ECS) zu programmieren. Ich habe, damit die verschiedenen Objekte (Entities) nicht während der Laufzeit initialisiert werden müssen, diese in einer Liste mit Vorlagen gespeichert und kann sie bei Bedarf herausholen, also kopieren (wird auch "EntityPool" oder "EntityFactory" genannt).
Hier liegt aber auch schon das Problem: Die Komponenten-Liste der neu erstellten Einheit ist natürlich nur eine Referenz auf die Komponenten-Liste der Vorlage. Also wird ja die Vorlage mitverändert, wenn eine Komponente verändert wird, was natürlich überhaupt nicht gewünscht ist. 
Wie kann ich also von einer Java-Collection eine "deep copy" machen, ohne in jeder der speziellen Komponenten-Klassen eine "clone()"-Methode einführen zu müssen?

Vielen Dank für jegliche Hilfe.


----------



## Schmetterhand (4. Jan 2017)

Oder generell formuliert:
Wie klone ich den Inhalt einer Liste ("deep copy"), ohne für alle darin enthaltenen Objekttypen eine "clone()"-Funktion zu haben und diese beim Klonen rekursiv aufzurufen?


----------



## thecain (4. Jan 2017)

gib in der Factory halt immer ein neues Objekt zurück, nicht das selbe


----------



## JuKu (5. Jan 2017)

Ich glaube du kommst um clone() nicht herum, es sei denn, du arbeitest mit ByteBuffer, sun.misc.Unsafe o.ä.

Vllt. funktioniert folgendes:

```
public ObjectName clone () {
    return (ObjectName) super.clone();
}
```


----------



## Schmetterhand (5. Jan 2017)

@thecain: Ich gebe bereits ein neues Objekt zurück, das aus der Vorlage heraus erstellt wurde. Das Problem ist, die Komponenten des neuen Objektes sind eine Referenz auf diejenigen der Vorlage, also wird diese mitverändert…

@JuKu: Ahja, danke, das "super.clone()" probier ich mal! (mit ByteBuffer etc. fange ich gleich gar nicht an )


----------



## JuKu (7. Jan 2017)

Oder du implementierst einfach ne copy() Methode, wo du ne neue Instanz erstellst.


----------



## thecain (7. Jan 2017)

Oder immutable Objects, welche bei einer änderung eine neue instanz zurückgeben. Oder einen copy Constructor.. gibt viele möglichkeiten.


----------



## Schmetterhand (8. Jan 2017)

Danke für die vielen Antworten. Ich fahre jetzt mit der "super.clone()"-Methode von Juku, denn das ist am einfachsten (bei einer "copy()"-Methode müßte ich ja alle Felder selber setzen?). Ich muß dann lediglich rekursiv alle Unter-Objekte in den zu klonenden Klassen auch noch Cloneable implementieren lassen und in deren "clone()"-Funktion wieder "super.clone()" aufrufen.
Schade, daß es keinen einfacheren Weg gibt…
Aber damit ist das Problem gelöst.


----------



## JuKu (9. Jan 2017)

Kannst ja dann mal hier rein schreiben, ob das ganze Konzept so funktioniert.


----------



## Schmetterhand (29. Jan 2017)

@Juku:
Also die "clone()"-Methoden funktionieren wunderbar, da gibt es nichts.
Aber ich glaube, daß für dieses relativ kleine Projekt auch eine altbewährte OOP-Herangehensweise gereicht hätte; so war es jetzt nur ein unnötig großer Aufwand beim erstellen der ECS-Architektur 
Aber natürlich hat diese auch Vorteile, man ist wirklich ziemlich frei in der Erstellung verschiedener Objekt-Typen etc., jedoch sind die einzelnen Systeme sehr stark abgekapselt und ich mußte extra ein "Messaging"-System einführen, um sauber zwischen ihnen kommunizieren zu können.
Naja, dafür bin ich jetzt eine Erfahrung weiter


----------

