Created
March 19, 2019 17:15
-
-
Save hellofromtonya/53ca2cd768238eed86421c3fe0b55763 to your computer and use it in GitHub Desktop.
Exploring PHP Variables, recount, and copy on write.
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
<?php | |
add_action( 'init', function() { | |
/** | |
* 1. PHP adds the variable into the symbols table. | |
* 2. PHP adds the value into the data table, which is called zval. | |
* 3. PHP points the value location to the variable location, binding them together. | |
* 4. refcount is incremented to 1. | |
*/ | |
$item_1 = 'something'; | |
/** | |
* Let's look at the zval for the variable $item_1: | |
* | |
* The output is: | |
* | |
* item_1: | |
* (refcount=1, is_ref=0),string 'something' (length=9) | |
* | |
* Notice the value is 'something' and the refcount is 1, meaning 1 variable is pointing to that memory location. | |
*/ | |
xdebug_debug_zval( 'item_1' ); | |
/** | |
* 1. PHP adds the variable into the symbols table. | |
* 2. PHP points the variable to the existing zval, i.e. value in memory. | |
* Why? To optimize memory usage. Instead of creating a new memory location (zval) for the value, it points | |
* to the same value that $item_1 is pointing to. | |
* 3. refcount for the value is incremented to 2. | |
*/ | |
$item_2 = $item_1; | |
/** | |
* Let's look at the zval for the variable $item_1. The output is: | |
* | |
* item_1: | |
* (refcount=2, is_ref=0),string 'something' (length=9) | |
* | |
* Notice the value is 'something' and the refcount is 2, meaning 2 variables are pointing to that memory location, | |
* i.e. $item_1 and $item_2. | |
*/ | |
xdebug_debug_zval( 'item_1' ); | |
/** | |
* Let's look at the zval for the variable $item_2. The output is: | |
* | |
* item_2: | |
* (refcount=2, is_ref=0),string 'something' (length=9) | |
* | |
* Notice that's the same as $item_1. Why? They are both pointing to the exact same value memory location. | |
*/ | |
xdebug_debug_zval( 'item_2' ); | |
/** | |
* Now let's change the value in one of the variables and see what happens. | |
* | |
* 1. PHP creates a new memory location in the data table, i.e. creates a new zal container. | |
* 2. It then points $item_1's memory location in the symbols table to the new location of where the value | |
* lives in memory (the new zval). | |
* 3. It increments the new value's refcount to 1, as only one variable is pointing to it. | |
* 4. It decrements the old value's refcount by 1, as $item_1 is no longer pointing to it. | |
* | |
* This process is known as Copy on Write. It's used to optimize memory. | |
*/ | |
$item_1 = 'something else'; | |
/** | |
* Let's look at the zval for the variable $item_1. The output is: | |
* | |
* item_1: | |
* (refcount=1, is_ref=0),string 'something else' (length=14) | |
* | |
* Notice the recount and value match what we'd expect. | |
*/ | |
xdebug_debug_zval( 'item_1' ); | |
/** | |
* Let's look again at the zval for the variable $item_2. The output is: | |
* | |
* item_2: | |
* (refcount=1, is_ref=0),string 'something' (length=9) | |
* | |
* Notice that the refcount is 1 and the value didn't change. | |
*/ | |
xdebug_debug_zval( 'item_2' ); | |
die(); | |
}); |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment