🐶
PHP

PHP Array Copy: How to Duplicate an Array

By Filip on 10/29/2024

Learn how to efficiently create duplicates of PHP arrays using built-in functions to avoid unexpected data modifications.

PHP Array Copy: How to Duplicate an Array

Table of Contents

Introduction

In PHP, copying arrays is a common task, but it's important to understand the nuances involved to avoid unexpected behavior. There are several ways to copy an array, each with its own implications for how changes to one array affect the other.

Step-by-Step Guide

In PHP, copying arrays can be done in a few ways, depending on what you want to achieve.

Simple Copy:

For a simple copy, where modifying the copy doesn't affect the original, direct assignment works:

$original = [1, 2, 3];
$copy = $original;

This creates a new array, $copy, with the same values as $original. Changes to one won't affect the other.

Reference:

If you want changes to one array to reflect in the other, use & to create a reference:

$original = [1, 2, 3];
$reference = &$original;

Now, $reference and $original point to the same array in memory. Modifying one modifies both.

Deep Copy (for arrays containing objects):

If your array contains objects and you need a completely independent copy, you'll need to do a deep copy. A simple way is to use serialize() and unserialize():

$deepCopy = unserialize(serialize($original)); 

This creates a new array with copies of the original objects.

Other Methods:

  • array_merge() can create a new array by merging existing arrays.
  • ArrayObject::getArrayCopy() returns a copy of the array represented by an ArrayObject object.

Remember to choose the method that suits your needs, considering whether you want a copy, a reference, or a deep copy.

Code Example

This PHP code demonstrates different methods of copying arrays. It shows examples of simple copy, reference, deep copy using serialization, and other methods like array_merge and ArrayObject::getArrayCopy. Each example includes the code and its output, illustrating how modifications to the copied array affect the original array. The code aims to provide a clear understanding of different array copying techniques and their implications.

<?php

// Simple Copy
$original = [1, 2, 3];
$copy = $original;

$copy[] = 4; 

echo "Original: ";
print_r($original); // Output: Original: Array ( [0] => 1 [1] => 2 [2] => 3 )
echo "<br>";

echo "Copy: ";
print_r($copy);     // Output: Copy: Array ( [0] => 1 [1] => 2 [2] => 3 [3] => 4 )
echo "<br><br>";

// Reference
$numbers = [5, 6, 7];
$reference = &$numbers;

$reference[] = 8;

echo "Numbers: ";
print_r($numbers);   // Output: Numbers: Array ( [0] => 5 [1] => 6 [2] => 7 [3] => 8 ) 
echo "<br>";

echo "Reference: ";
print_r($reference); // Output: Reference: Array ( [0] => 5 [1] => 6 [2] => 7 [3] => 8 )
echo "<br><br>";

// Deep Copy (with objects)
class Product {
    public $name;

    public function __construct($name) {
        $this->name = $name;
    }
}

$product1 = new Product("Coffee");
$product2 = new Product("Tea");

$products = [$product1, $product2];
$deepCopy = unserialize(serialize($products));

$deepCopy[0]->name = "Hot Chocolate"; 

echo "Original Products: ";
print_r($products); // Output: Original Products: Array ( [0] => Product Object ( [name] => Coffee ) [1] => Product Object ( [name] => Tea ) )
echo "<br>";

echo "Deep Copy Products: ";
print_r($deepCopy); // Output: Deep Copy Products: Array ( [0] => Product Object ( [name] => Hot Chocolate ) [1] => Product Object ( [name] => Tea ) )
echo "<br><br>";

// Other Methods
$array1 = [1, 2];
$array2 = [3, 4];

// array_merge()
$merged = array_merge($array1, $array2);
echo "Merged: ";
print_r($merged); // Output: Merged: Array ( [0] => 1 [1] => 2 [2] => 3 [3] => 4 )
echo "<br>";

// ArrayObject::getArrayCopy()
$arrayObject = new ArrayObject(['a', 'b']);
$arrayCopy = $arrayObject->getArrayCopy();
echo "Array Copy: ";
print_r($arrayCopy); // Output: Array Copy: Array ( [0] => a [1] => b ) 

?>

Explanation:

  1. Simple Copy: We create $copy as a simple copy of $original. Modifying $copy doesn't change $original.
  2. Reference: $reference becomes a reference to $numbers. Changes to either affect both.
  3. Deep Copy: We use serialize() and unserialize() to create a deep copy of the $products array, which contains objects. Modifying an object in the $deepCopy array doesn't affect the original $products array.
  4. Other Methods: We demonstrate using array_merge() to combine arrays and ArrayObject::getArrayCopy() to get a copy of an array from an ArrayObject.

This code provides clear examples of different array copying techniques in PHP, helping you understand when to use each method.

Additional Notes

  • Copy-on-write mechanism: PHP uses a copy-on-write mechanism for arrays. This means that when you make a simple copy of an array, both the original and the copy initially point to the same data in memory. Only when you modify one of the arrays does PHP create a separate copy of the data. This optimization saves memory and improves performance.
  • Shallow copy vs. deep copy: It's crucial to understand the difference between shallow and deep copying, especially when dealing with arrays containing objects. A shallow copy creates a new array with references to the same objects as the original array. In contrast, a deep copy creates a new array with copies of the original objects, ensuring that changes to objects in one array don't affect the other.
  • Alternatives to serialize() for deep copying: While serialize() and unserialize() offer a straightforward way to deep copy arrays, they might not be suitable for all situations, especially when dealing with large arrays or objects that cannot be serialized. Other options for deep copying include:
    • Using a loop to iterate through the original array and manually create copies of each element.
    • Leveraging PHP's clone keyword to create deep copies of objects within the array.
  • Performance considerations: The performance of different array copying methods can vary depending on the size and structure of the array. For instance, using array_merge() to copy an array is generally less efficient than a simple assignment, especially for large arrays.
  • Choosing the right method: The best method for copying an array depends on the specific use case. Consider the following factors:
    • Do you need a copy or a reference?
    • Does the array contain objects?
    • How deep do you need the copy to be?
    • What are the performance implications of each method?
  • Debugging tips: When working with arrays and copying, it's helpful to use print_r() or var_dump() to inspect the contents of arrays at different stages of your code. This can help you understand how changes to one array are affecting others and identify potential issues.

Summary

Method Description Affects Original? Deep Copy?
Direct Assignment $copy = $original; No No
Reference $reference = &$original; Yes No
serialize/unserialize $deepCopy = unserialize(serialize($original)); No Yes
array_merge() Creates a new array by merging existing arrays. No Depends*
ArrayObject::getArrayCopy() Returns a copy of the array represented by an ArrayObject object. No No

Notes:

  • Deep Copy: Necessary when the array contains objects and you need completely independent copies.
  • array_merge(): Creates a deep copy only if the merged arrays contain objects. Otherwise, it's a shallow copy.

Choose the method that best suits your needs based on whether you want a simple copy, a reference, or a deep copy.

Conclusion

Understanding how PHP handles array copying, particularly the differences between shallow and deep copies, is crucial for writing predictable and maintainable code. Choosing the appropriate copying method depends on the specific context and whether modifications to the copy should impact the original array. While simple assignments are suitable for creating independent copies of arrays with scalar values, deep copying methods like serialize/unserialize or manual element cloning become essential when dealing with arrays containing objects to ensure true independence and prevent unintended side effects. Remember to consider performance implications, especially for large arrays, and leverage debugging tools to inspect array contents and confirm the desired behavior. By mastering these concepts, developers can confidently manipulate arrays in PHP, knowing that their data is handled as intended.

References

I have two struct varriables, that have arrays of other struct. The first array is the base on which the second structure is based.

Then the game do stuff with values in array of second struct. Intentions are that the values in first struct remain unchanged...

Were You Able to Follow the Instructions?

😍Love it!
😊Yes
😐Meh-gical
😞No
🤮Clickbait