note 59811 added to language.functions
| From: | budzynowski at hot dot NOSPAM dot mail dot com | Date: | Fri, 16 Dec 2005 07:56:03 +0000 |
| Subject: | note 59811 added to language.functions | ||
| Groups: | php.notes | ||
| Request: | Send a blank email to php-notes+get-100295@lists.php.net to get a copy of this message | ||
If you're having stack problems with recursive subroutines, you can just make your own stack.
Simply use an array, to which you add a value that you need to return to later. (I.e. rather than
calling the function again, save the variables you would pass to it into an array) When you would
normally 'return', just load up the last set of values from the array and continue from
there.
array_push() and array_pop() may be helpful.
Here is yasuo_ohgaki AT hotmail DOT com's program modified to use no recursion:
<?php
echo('<br>Recursion-free TEST<br>');
function swap(&$v, $i, $j) {
$temp = $v[$i];
$v[$i] = $v[$j];
$v[$j] = $temp;
}
// Quick Sort integer array - $int_array[$left] .. $int_array[$right]
function qsort(&$int_array, $left, $right) {
for(;;){ //keep repeating this until we reach return statement
while ($left >= $right){
if (($right=array_pop($stack))==NULL) return; // Quit if the array is empty
$left=array_pop($stack); //Otherwise load another $left and $right to process
}
swap ($int_array, $left, intval(($left+$right)/2));
$last = $left;
for ($i = $left + 1; $i <= $right; $i++)
if ($int_array[$i] < $int_array[$left])
swap($int_array, ++$last, $i);
swap($int_array, $left, $last);
$stack[]=$left; // Store the left and right values we need to process later
$stack[]=$last-1;
$left=$last+1; //$right is unchanged.
}
}
$val = array(406,12,92,1,75,237,1,16,55,23,204,2,14,16);
qsort($val, 0, count($val)-1);
echo '<pre>';
print_r ($val);
echo '</pre>';
?>
Also, some algorithms perform better when you *don't* stick to the order in the stack, by
"typing up loose ends", as I have found with floodfill algorithms, for example. You can
either pick and remove random stack elements, or swap a random element with the last one, then pop
it off.
One other thing- don't use recursion unless it gives a large advantage, as there is quite a bit
of overhead in calling functions. germanAlonso at keltoi-web dot com's factorial program is
fine as a demonstration of recursion, but I think a method like this would be more efficient:
function fact($i){
for($j = $i; $j; $i*=$j--){}
return $i;
}
----
Manual Page -- http://www.php.net/manual/en/language.functions.php
Edit -- http://master.php.net/manage/user-notes.php?action=edit+59811
Delete: added to the manual -- http://master.php.net/manage/user-notes.php?action=delete+59811&report=yes&reason=added+to+the+manual
Delete: bad code -- http://master.php.net/manage/user-notes.php?action=delete+59811&report=yes&reason=bad+code
Delete: spam -- http://master.php.net/manage/user-notes.php?action=delete+59811&report=yes&reason=spam
Delete: useless -- http://master.php.net/manage/user-notes.php?action=delete+59811&report=yes&reason=useless
Delete: non-english -- http://master.php.net/manage/user-notes.php?action=delete+59811&report=yes&reason=non-english
Delete: already in docs -- http://master.php.net/manage/user-notes.php?action=delete+59811&report=yes&reason=already+in+docs
Delete: other reasons -- http://master.php.net/manage/user-notes.php?action=delete+59811&report=yes
Reject -- http://master.php.net/manage/user-notes.php?action=reject+59811&report=yes
Search -- http://master.php.net/manage/user-notes.php