2.25.  Cloning objects

[Warning]Text not verified for kermeta 2

As we saw in previous sections, class properties can be defined as attribute or reference. An attribute cannot be shared between two or more objects whereas a reference can be. Let's consider a class " Family " with a property " father " (of type " Person ") defined as an attribute. In the following example, we defined two objects of type Family and we want to define the father attribute of the second with the father of the first. To do that, we need to clone the object Person which represents the father of " family1 " because, as said in Section 2.16.6, “Assignment behavior for attribute (and reference)” , it could not be shared between the two objects, by definition of attribute (in "technical" words, an object cannot be contained by 2 containers).

class Person 
{
     attribute name : String
}
class Family
{
    attribute father : Person
}

class Main
{
    operation run() is
    do var family1 : Family init Family.new
       var p1 : Person init Person.new
       p1.name := "Robert"
       family1.father := p1
 var family2 : Family init Family.new

       // ERROR 1 : this assigns p1 to family2.father, which 
       // is already owned by family1.father, so it unsets family1.father 
       // family2.father := p1

       // ERROR 2 : this assigns family1.father's value to family2.father, 
       // so it unsets family1.father 
       // family2.father := family1.father

       // This is correct! family2.father keeps its value
       family2.father := Person.clone(p1)
    end
}

The " clone " method creates a copy of the object that it receives as input. If it is a complex object, a deep clone is performed for each attribute of its meta-class and a shallow clone is performed for each reference.

[Caution]Caution

Reminder : be very careful with the use of the assignment operator on object. Most of the time, you need to use the "clone" feature. Using assignment on attributes break the previous link between objects. So, In the previous example, p1 has no more name after the assignment !There is one exception to this behavior : when the type of attributes are DataType, i.e, in Kermeta, String, Integer, Boolean, the assignment behaves as if those entities were defined as references.