How do I create a copy of an object in PHP?

Viewed 150369

It appears that in PHP objects are passed by reference. Even assignment operators do not appear to be creating a copy of the Object.

Here's a simple, contrived proof:

<?php

class A {
    public $b;
}


function set_b($obj) { $obj->b = "after"; }

$a = new A();
$a->b = "before";
$c = $a; //i would especially expect this to create a copy.

set_b($a);

print $a->b; //i would expect this to show 'before'
print $c->b; //i would ESPECIALLY expect this to show 'before'

?>

In both print cases I am getting 'after'

So, how do I pass $a to set_b() by value, not by reference?

9 Answers

In PHP 5+ objects are passed by reference. In PHP 4 they are passed by value (that's why it had runtime pass by reference, which became deprecated).

You can use the 'clone' operator in PHP5 to copy objects:

$objectB = clone $objectA;

Also, it's just objects that are passed by reference, not everything as you've said in your question...

The answers are commonly found in Java books.

  1. cloning: If you don't override clone method, the default behavior is shallow copy. If your objects have only primitive member variables, it's totally ok. But in a typeless language with another object as member variables, it's a headache.

  2. serialization/deserialization

$new_object = unserialize(serialize($your_object))

This achieves deep copy with a heavy cost depending on the complexity of the object.

According to previous comment, if you have another object as a member variable, do following:

class MyClass {
  private $someObject;

  public function __construct() {
    $this->someObject = new SomeClass();
  }

  public function __clone() {
    $this->someObject = clone $this->someObject;
  }

}

Now you can do cloning:

$bar = new MyClass();
$foo = clone $bar;

In this example we will create iPhone class and make exact copy from it by cloning

class iPhone
{
    public $name;
    public $email;

    public function __construct($n, $e) {

       $this->name = $n;
       $this->email = $e;

    }
}

$main = new iPhone('Dark', 'm@m.com');
$copy = clone $main;

// if you want to print both objects, just write this    

echo "<pre>"; print_r($main);  echo "</pre>";
echo "<pre>"; print_r($copy);  echo "</pre>";
Related