1

I have some code that appears to behave differently between PHP 4 and PHP 5. This code below:

class CFoo
{
    var $arr;

    function CFoo()
    {
        $this->arr = array();
    }

    function AddToArray($i)
    {
        $this->arr[] = $i;
    }

    function DoStuffOnFoo()
    {
        for ($i = 0; $i < 10; ++$i)
        {
            $foo2 = new CFoo();
            $foo2 = $this;          // I expect this to copy, therefore
                                    // resetting back to the original $this
            $foo2->AddToArray($i);
            echo "Foo2:\n";
            print_r($foo2);
            echo "This:\n";
            print_r($this);
        }
    }
}

$foo1 = new CFoo();
$foo1->DoStuffOnFoo();

Previously, in PHP 4, the assignment of $foo2 above would reset $foo2 back to the value that $this was originally set at. In this case, I would expect it to be set to a CFoo with an empty $arr member. However, the assignment of $foo2 to $this is acting as an assignment by reference. Foo2 is acting as an alias to this. Therefore when I call "AddToArray" on foo2, $this's $arr is also being appended to. So when I go to reassign foo2 back to this, instead of getting the initial value of this, I get essentially a self assignment.

Has this behavior changed in PHP 5? What can I do to force foo2 to make a copy of this?

4 Answers 4

3

The object-oriented part of PHP has been hugely overhauled in PHP 5. Objects are now passed (not exactly but almost) as references. See http://docs.php.net/clone.

Example:

$x1 = new StdClass;
$x1->a = 'x1a';

$x2 = $x1;
$y = clone $x1;

// Performing operations on x2 affects x1 / same underlying object
$x2->a = 'x2A';
$x2->b = 'x2B';

// y is a clone / changes do not affect x1
$y->b = 'yB';

echo 'x1: '; print_r($x1);
echo 'y:'; print_r($y);

prints

x1: stdClass Object
(
    [a] => x2A
    [b] => x2B
)
y:stdClass Object
(
    [a] => x1a
    [b] => yB
)
Sign up to request clarification or add additional context in comments.

Comments

3

In PHP 4 a copy was made of an object iunless you assigned it by reference (using &=). In PHP 5 a reference to the object is assigned.

So after assigning $this to $foo2, $foo2 points to $this and not to a new copy of CFoo.

To make a copy in PHP 5 you say clone $this.

In either case, the previous new statement is wasted.

Comments

2

Yes, PHP 5 is now copying by reference. Now you have to clone the object to make a copy of it.

Comments

1

PHP has used references since version 5. To copy objects, use:

$copy = clone $object;

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.