|  Topic awaiting preservation: PHP seems to "forget" changes made to an array in a loop.  | |
|---|---|
| Author | Thread | 
| Nervous Wreck (II) Inmate From: United States |  posted 04-09-2009 23:26 I'm trying to make a code for a game site that will convert strings resembling the following... code: *Legend of Zelda: Ocarina of Time **Index **Glitches ***Swordless Link ****Poe Link ***Steal the Fishing Rod **Videos **Guides **Secrets **Cheats 
 code: array(
   'Legend of Zelda: Ocarina of Time'=>
      array(
         'Index'=>array(),
         'Glitches'=>
            array(
               'Swordless Link'=>
                  array(
                     'Poe Link'=>array()
                  ),
               'Steal the Fishing Rod'=>array()
            ),
         'Videos'=>array(),
         'Guides'=>array(),
         'Secrets'=>array(),
         'Cheats'=>array()
      )
);
 code: <pre><?php
function OutputTreeView($treeString,$root=0) {
   $treeData=explode("\n",$treeString); // array of lines
   $tree = array();
   $curs = array();
   $offset = 0; // not important
   if($root) { // FROM HERE TO THE NEXT COMMENT... IS NOT IMPORTANT.
      $line=$treeData[0];
      $offset=strspn($line,'*');
      $level=0;
      $tree[substr($line,$level+$offset)] = array();
      $curs[$level]=substr($line,$level+$offset);
      array_shift($treeData);
   } else {
      $level=0;
      $line='';
      $tree['[root]']=array();
      $curs[$level]='[root]';
   } // FROM HERE TO THE PREVIOUS COMMENT IS NOT IMPORTANT.
   foreach($treeData as $line) {
      $level= strspn($line,'*')-$offset; // use the "*"s at the beginning to determine how nested we are.
      $curs[$level]=substr($line,$level+$offset); // used to keep track of where we are in $tree, so that we can build $varString
      $varString = '$tree['; // prepare for variable substitution (the double dollar sign trick)
      for($i=0;$i<=$level;$i++) {
         $varString.="'".$curs[$i]."']";
         if($i<$level) { $varString.='['; }
      }
      $$varString = array(); // the actual variable substitution, used to alter $tree
      // [debug statement removed]
      if($level+1<count($curs)) { // this IF and the WHILE inside of it is only NEEDED for debugging.
         while(count($curs)>$level+1) { array_pop($curs); }
      }
   }
   return $tree;
}
$TREE='*Legend of Zelda: Ocarina of Time'."\n".'**Index'."\n".
'**Glitches'."\n".'***Swordless Link'."\n".'****Poe Link'."\n".
'***Steal the Fishing Rod'."\n".'**Videos'."\n".'**Guides'."\n".
'**Secrets'."\n".'**Cheats';
// The string example I presented above. I woulda used a nowdoc, 
// but PHP was throwing a T_SL error even though there was nothing 
// wrong with the syntax (I Googled the error to figure out the cause, 
// and the cause wasn't present) -- ah, well.
echo OutputTreeView($TREE);
?></pre>
 code: Function invoked!
$treeString ==
*Legend of Zelda: Ocarina of Time
**Index
**Glitches
***Swordless Link
****Poe Link
***Steal the Fishing Rod
**Videos
**Guides
**Secrets
**Cheats
$root == 1 so "*Legend of Zelda: Ocarina of Time" is the "root" of this list, and $offset = 1.
   Iteration! $level==1, $line==**Index,
      $varString==$tree['Legend of Zelda: Ocarina of Time']['Index']
      [here, we set $$varString = array()]
      $$varString==Array
   Iteration! $level==1, $line==**Glitches,
      $varString==$tree['Legend of Zelda: Ocarina of Time']['Glitches']
      [here, we set $$varString = array()]
      $$varString==Array
   Iteration! $level==2, $line==***Swordless Link,
      $varString==$tree['Legend of Zelda: Ocarina of Time']['Glitches']['Swordless Link']
      [here, we set $$varString = array()]
      $$varString==Array
   Iteration! $level==3, $line==****Poe Link,
      $varString==$tree['Legend of Zelda: Ocarina of Time']['Glitches']['Swordless Link']['Poe Link']
      [here, we set $$varString = array()]
      $$varString==Array
   Iteration! $level==2, $line==***Steal the Fishing Rod,
      $varString==$tree['Legend of Zelda: Ocarina of Time']['Glitches']['Steal the Fishing Rod']
      [here, we set $$varString = array()]
      $$varString==Array
   Iteration! $level==1, $line==**Videos,
      $varString==$tree['Legend of Zelda: Ocarina of Time']['Videos']
      [here, we set $$varString = array()]
      $$varString==Array
   Iteration! $level==1, $line==**Guides,
      $varString==$tree['Legend of Zelda: Ocarina of Time']['Guides']
      [here, we set $$varString = array()]
      $$varString==Array
   Iteration! $level==1, $line==**Secrets,
      $varString==$tree['Legend of Zelda: Ocarina of Time']['Secrets']
      [here, we set $$varString = array()]
      $$varString==Array
   Iteration! $level==1, $line==**Cheats,
      $varString==$tree['Legend of Zelda: Ocarina of Time']['Cheats']
      [here, we set $$varString = array()]
      $$varString==Array
Function complete.
And when we print_r $tree, we see:
(
    [Legend of Zelda: Ocarina of Time] => Array
        (
        )
)
...Which is weird, because $tree['Legend of Zelda: Ocarina of Time'] shouldn't be empty.
And when we print_r $$varString, we see:
Array
(
)
Which makes sense.
And when we print_r $curs, we see:
Array
(
    [0] => Legend of Zelda: Ocarina of Time
    [1] => Cheats
)
 | 
| Maniac (V) Mad Scientist with Finglongers From: Germany |  posted 04-10-2009 08:55 I will bet even money that your $$ magic doesn't do what you think it does. code: function createTree($lines, $depth = 1)
{
if (!is_array($lines))
  $lines = split("\n", lines);
$tree = array();
while (count($lines) > 0 )
{
$nextLine = array_unshift($lines);
$newDepth = strspn($nextLine,'*');
$lineName = substr($nextLine, $newDepth);
if ($newDepth == $depth)
{
   $tree[$lineName] = array();
   $lastName = &$lineName;
}
else
{
  $tree[$lineName] = createTree($lines, $depth + 1);
}
return $tree;
}
 |