Nathan Rixham wrote:
Ford, Mike wrote:
-----Original Message-----
From: Rene Veerman [mailto:rene7705@xxxxxxxxx]
Sent: 27 January 2010 22:46
And if your script needs to pass large (> 5Mb) arrays around to
functions, be sure to use passing-by-reference; failing to do so can
double your memory requirements,
possibly hitting the ini_set('memory_lmit', ??)
Have you benchmarked this? PHP's copy-on-change philosophy means there shouldn't be much difference in memory terms -- so unless you actually expect to change the array's contents, you should pass by value.
As proof, I constructed this little test:
function test($arg, $base_mem)
{
echo "Additional inside func = ", memory_get_usage()-$base_mem, "<br />\n";
}
try changing this to access the array in some way such as:
function test($arg, $base_mem)
{
foreach( $arg as $index => $value ) {
}
echo "Additional= ", memory_get_usage()-$base_mem, "\n";
}
After array creation = 52696
Additional = 101152
Final = 117200
vs: function test(&$arg, $base_mem)
After array creation = 52696
Additional = 53104
Final = 101696
there's the double memory usage
I don't know what you guys are doing wrong but the following should be
the correct behaviour:
<?php
function get_memory( $init=false )
{
static $base = null;
if( $base === null || $init )
{
$base = memory_get_usage();
}
return memory_get_usage() - $base;
}
function simple_access( $data )
{
$foo = $data[100];
echo 'Memory: '.get_memory().' (simple access)'."\n";
}
function foreach_value_access( $data )
{
foreach( $data as $value )
{
$foo = $value;
break;
}
echo 'Memory: '.get_memory().' (foreach value access)'."\n";
}
function foreach_key_access( $data )
{
foreach( $data as $key => $value )
{
$foo = $key;
$foo = $value;
break;
}
echo 'Memory: '.get_memory().' (foreach key/value access)'."\n";
}
function modify_single_access( $data )
{
$data[100] = str_repeat( '@', 10000 );
echo 'Memory: '.get_memory().' (modify single access)'."\n";
}
function modify_all_access( $data )
{
for( $i = 0; $i < 1000; $i++ )
{
$data[$i] = str_repeat( '@', 10000 );
}
echo 'Memory: '.get_memory().' (modify all access)'."\n";
}
get_memory( true );
$data = array();
for( $i = 0; $i < 1000; $i++ )
{
$data[$i] = str_repeat( '#', 10000 );
}
echo 'Memory: '.get_memory().' (data initialized)'."\n";
simple_access( $data );
foreach_value_access( $data );
foreach_key_access( $data );
modify_single_access( $data );
modify_all_access( $data );
?>
I get the following output (PHP 5.2.11 from command-line):
Memory: 10160768 (data initialized)
Memory: 10161008 (simple access)
Memory: 10161104 (foreach value access)
Memory: 10161240 (foreach key/value access)
Memory: 10267312 (modify single access)
Memory: 20321576 (modify all access)
I don't double up on memory consumption until I force the write onto
every element... this is expected because internally every array element
is individually subject to the Copy-On-Write (COW) principle since each
element is internally stored as a zval just like the array itself.
Cheers,
Rob.
--
http://www.interjinn.com
Application and Templating Framework for PHP
--
PHP General Mailing List (http://www.php.net/)
To unsubscribe, visit: http://www.php.net/unsub.php