First look at the unset function syntax
unset
Deletes a variable.
Syntax: int unset (mixed Var);
return value: Integer
Function type: PHP system function
Content Description
This function deletes the variable and returns a true value for success.
First let's look at an example
Var_dump (Memory_get_usage ());
$a = "laruence";
Var_dump (Memory_get_usage ());
unset ($a);
Var_dump (Memory_get_usage ());
The output (on my PC, may vary depending on the system, PHP version, load extension):
Int (90440)
Int (90640)
Int (90472
Note that 90472-90440=32, so there are a variety of conclusions, some people say that PHP unset does not really release memory, some say, PHP unset only in the release of large variables (a large number of strings, large arrays) when the real free memory, more people say, There is no point in discussing memory at the PHP level.
So, in the end unset will not release memory? Where did the 32 bytes go?
To answer this question, I'll start with two things:
Where did these 32 bytes go?
First we have to break a thinking: PHP is not like C language, only you show the call memory allocation related APIs will have memory allocation.
In other words, in PHP, there are many memory allocation processes that we don't see.
For example:
$a = "laruence";
The implicit memory allocation points are:
1. Allocate memory for variable name, save in symbol table
2. Assign the value of the variable
So, you can't just look at appearances.
Second, do not doubt that the PHP unset does release memory (of course, with reference and counting, this part of the content please see my previous article in-depth understanding of the PHP principle of the variable separation/reference), but this release is not a C programming sense of release, not handed back to the OS.
For PHP itself, it offers a set of memory management APIs similar to the C language for memory allocations, which correspond to the API meaning of C, which is used internally by these APIs to manage memory.
When we call Emalloc to request memory, PHP is not simply to the OS to the memory, but will be like the OS to a large chunk of memory, and then put a piece of it to the requester, so that when there is logic to apply for memory, it will no longer need to apply memory to the OS, avoid frequent system calls.
Examples include the following:
<?php
Var_dump (Memory_get_usage (TRUE)); Note that the acquisition is Real_size
$a = "laruence";
Var_dump (Memory_get_usage (TRUE));
unset ($a);
Var_dump (Memory_get_usage (TRUE));
Output:
Int (262144)
Int (262144)
Int (262144
That is, when we define variable $a, PHP does not request new memory from the system.
Similarly, when we call Efree to release the memory, PHP will not return the memory to the OS, but will put this memory into its own maintenance of the free memory list. And for small chunks of memory, it's more likely that you put it in the memory cache list (PostScript, some versions of PHP, such as PHP5.2.4, 5.2.6, and 5.2.8 that I've validated, when I call Get_memory_usage (), The free memory block size in the memory cache list is not subtracted, resulting in the appearance of unset memory.
Now let me answer these 32 bytes where to go, just to say to me, a lot of memory allocation process is not explicit, look at the following code you understand:
<?php
Var_dump ("I am Www.111cn.net");
Var_dump (Memory_get_usage ());
$a = "laruence";
Var_dump (Memory_get_usage ());
unset ($a);
Var_dump (Memory_get_usage ());
Output:
String ("I am Www.111cn.net")
Int (90808)//before assignment
Int (90976)
Int (90808)/Yes, memory normal release
90808-90808 = 0, normal, which means that the 32 bytes are occupied by the output function (strictly speaking, the header is occupied by the output)
An array that is only added and not reduced
Hashtable is the core structure of PHP (for Hashtable, see my previous article for an in-depth understanding of the PHP array (traversal order), the array is represented by her, and the symbol table is an associative array, for the following code:
Var_dump ("I am Www.111cn.net");
Var_dump (Memory_get_usage ());
$array = Array_fill (1, "laruence");
foreach ($array as $key => $value) {
${$value. $key} = NULL;
}
Var_dump (Memory_get_usage ());
foreach ($array as $key => $value) {
Unset (${$value. $key});
}
Var_dump (Memory_get_usage ());
We define 100 variables and then press a unset them to see the output:
String ("I am Www.111cn.net")
Int (93560)
Int (118848)
Int (104448
Wow, why is there so much memory missing?
This is because for Hashtable, when you define it, it is not possible to allocate enough chunks of memory at once to save an unknown number of elements, so PHP will be initialized, just allocate a small amount of memory block to Hashtable, when not enough to resize expansion,
And Hashtable, can only expand, will not be reduced, for the above example, when we deposit 100 variables, the symbol table is not enough, do a expansion, and when we sequentially unset the 100 variables, the variable occupies the memory is released (118848–104448), but The symbol table does not shrink, so these little memory is taken up by the symbol table itself ...
Now, do you have a rudimentary understanding of PHP's memory management?
If you don't get it, let's look at an example:
<?php
$s =str_repeat (' 1 ', 255); Produces a string consisting of 255 1
$m =memory_get_usage (); Get current memory footprint
Unset ($s);
$MM =memory_get_usage (); Unset () and then view current memory consumption
echo $m-$mm;
?>
After the final output unset () consumes memory minus unset () and if it is positive, then unset ($s) has destroyed $s from memory (or, after unset () the memory footprint is reduced), but I am under PHP5 and Windows platforms, The results are:-48. Does this indicate that unset ($s) does not play a role in destroying the memory occupied by the variable $s? Let us make the following example:
<?php
$s =str_repeat (' 1 ', 256); Produces a string consisting of 256 1
$m =memory_get_usage (); Get current memory footprint
Unset ($s);
$MM =memory_get_usage (); Unset () and then view current memory consumption
echo $m-$mm;
?>
This example is almost the same as the example above, the only difference being that the $s is made up of 256 1, that is, a 1 more than the first example, and the result is: 224. Does this indicate that unset ($s) has destroyed the memory occupied by $s?
With the above two examples, we can draw the following conclusions: conclusion one, unset () function frees up memory space only if the variable value occupies more than 256 bytes of memory space.
So as long as the value of the variable is more than 256, you can use unset to free up memory space? Let's test it again with an example:
<?php
$s =str_repeat (' 1 ', 256); This is exactly the same as the second example.
$p =& $s;
$m =memory_get_usage ();
Unset ($s); Destroy $s
$MM =memory_get_usage ();
echo $p. ' <br/> ';
echo $m-$mm;
?>
Refresh the page, we see the first row has 256 1, the second line is 48, we have destroyed the $s, and $p just reference $s variables, there should be no content, in addition, unset ($s) after the memory footprint than the unset () before the increase! Now let's take the following example:
<?php
$s =str_repeat (' 1 ', 256); This is exactly the same as the second example.
$p =& $s;
$m =memory_get_usage ();
$s =null; Set $s to null
$MM =memory_get_usage ();
echo $p. ' <br/> ';
echo $m-$mm;
?>
Now refresh the page, we see that the output $p has no content, unset () before and after the difference of memory footprint is 224, that is, the variable occupied memory has been cleared. The $s=null in this example can also be replaced by unset (), as follows:
<?php
$s =str_repeat (' 1 ', 256); This is exactly the same as the second example.
$p =& $s;
$m =memory_get_usage ();
Unset ($s); Destroy $s
Unset ($p);
$MM =memory_get_usage ();
echo $p. ' <br/> ';
echo $m-$mm;
?>
We use unset () to destroy both $s and $p, and then the difference between the memory footprint is also 224, which means that memory can also be freed. So, we can get another conclusion: Second, the memory is freed only when all variables (such as reference variables) that point to the variable are destroyed.