Re: [PHP] RecursiveArrayIterator
as i said earlier the purpose of an iterator is to hide the internal representation of an object. ive been thinking about it the past couple of days and the odd thing with php is, well in php, the array construct is used to store almost everything complex. in java there are lots of different data structures, ArrayList, HashMap, Vector, etc, etc. so its seems there is a more natural demand for iterators in java. however, if you create custom data structures around the array; queue, stack, and of course tree structures, etc. well then, iterators start making more sense for php. basically the funky SPL thing is all about design patterns and OOP. -nathan On 7/25/07, Richard Lynch [EMAIL PROTECTED] wrote: On Sun, July 22, 2007 9:02 pm, Kevin Waterson wrote: This one time, at band camp, Nathan Nobbe [EMAIL PROTECTED] wrote: Thanks for the response. I was hoping to avoid this sort of recursion within userspace and keep it at a lower level. Should not the recursive iterator recurse so we dont need to be using user defined functions? printArrayKeysRecursively($innerRecursiveArrayIterator); // handle printing I don't understand this SPL stuff (and don't want to, as it just gives me a headache to even look at the function names) but you've got this: $foo = array( array ( 'a', 'b', 'c')); So of course your outer array has 0 = [inner array] in it. How you get some funky SPL thing to only dump out the inner array is beyond me... There is an array_collapse or somesuch that will sort of smush all the sub-arrays into one big array, which might do what you want. Or not. -- Some people have a gift link here. Know what I want? I want you to buy a CD from some indie artist. http://cdbaby.com/browse/from/lynch Yeah, I get a buck. So? -- PHP General Mailing List (http://www.php.net/) To unsubscribe, visit: http://www.php.net/unsub.php
Re: [PHP] RecursiveArrayIterator
On Sun, July 22, 2007 9:02 pm, Kevin Waterson wrote: This one time, at band camp, Nathan Nobbe [EMAIL PROTECTED] wrote: Thanks for the response. I was hoping to avoid this sort of recursion within userspace and keep it at a lower level. Should not the recursive iterator recurse so we dont need to be using user defined functions? printArrayKeysRecursively($innerRecursiveArrayIterator); // handle printing I don't understand this SPL stuff (and don't want to, as it just gives me a headache to even look at the function names) but you've got this: $foo = array( array ( 'a', 'b', 'c')); So of course your outer array has 0 = [inner array] in it. How you get some funky SPL thing to only dump out the inner array is beyond me... There is an array_collapse or somesuch that will sort of smush all the sub-arrays into one big array, which might do what you want. Or not. -- Some people have a gift link here. Know what I want? I want you to buy a CD from some indie artist. http://cdbaby.com/browse/from/lynch Yeah, I get a buck. So? -- PHP General Mailing List (http://www.php.net/) To unsubscribe, visit: http://www.php.net/unsub.php
Re: [PHP] RecursiveArrayIterator
This one time, at band camp, Jim Lucas [EMAIL PROTECTED] wrote: I don't get it, why not do this? foreach ( $array AS $row ) { foreach ( $row AS $k = $v ) { if ( ! is_array($v) ) { echo {$k} -- {$v}br/\n; } } } Maybe I am missing the point... ??? Indeed, whilst your method is simplistic it leaves many copies of the array dangling in memory. Every time you call foreach it creates a copy of the array internally. SPL iterators do things differently and know only one element at a time. More can be seen at http://phpro.org/tutorials/Introduction-to-SPL.html so the final solution was using a foreach, however, using a foreach on an SPL iterator object implicitly calls the inner iterator giving us all the SPL goodness in memory savings. Kind regards Kevin -- Democracy is two wolves and a lamb voting on what to have for lunch. Liberty is a well-armed lamb contesting the vote. -- PHP General Mailing List (http://www.php.net/) To unsubscribe, visit: http://www.php.net/unsub.php
Re: [PHP] RecursiveArrayIterator
the purpose of an iterator is to allow client code to access the various (aggregate) components of an object while concealing its underlying implementation. the client code only has to know about the iterators interface. thus 1 or more objects that all have a potentially different data profile internally can expose something like a getIterator() method. then client code can interact cleanly with all such objects, because it knows only 1 interface, the iterator interface. http://en.wikipedia.org/wiki/Iterator -nathan On 7/23/07, Kevin Waterson [EMAIL PROTECTED] wrote: This one time, at band camp, Jim Lucas [EMAIL PROTECTED] wrote: I don't get it, why not do this? foreach ( $array AS $row ) { foreach ( $row AS $k = $v ) { if ( ! is_array($v) ) { echo {$k} -- {$v}br/\n; } } } Maybe I am missing the point... ??? Indeed, whilst your method is simplistic it leaves many copies of the array dangling in memory. Every time you call foreach it creates a copy of the array internally. SPL iterators do things differently and know only one element at a time. More can be seen at http://phpro.org/tutorials/Introduction-to-SPL.html so the final solution was using a foreach, however, using a foreach on an SPL iterator object implicitly calls the inner iterator giving us all the SPL goodness in memory savings. Kind regards Kevin -- Democracy is two wolves and a lamb voting on what to have for lunch. Liberty is a well-armed lamb contesting the vote. -- PHP General Mailing List (http://www.php.net/) To unsubscribe, visit: http://www.php.net/unsub.php
Re: [PHP] RecursiveArrayIterator
On Monday 23 July 2007, Kevin Waterson wrote: This one time, at band camp, Jim Lucas [EMAIL PROTECTED] wrote: I don't get it, why not do this? foreach ( $array AS $row ) { foreach ( $row AS $k = $v ) { if ( ! is_array($v) ) { echo {$k} -- {$v}br/\n; } } } Maybe I am missing the point... ??? Indeed, whilst your method is simplistic it leaves many copies of the array dangling in memory. Every time you call foreach it creates a copy of the array internally. SPL iterators do things differently and know only one element at a time. More can be seen at http://phpro.org/tutorials/Introduction-to-SPL.html so the final solution was using a foreach, however, using a foreach on an SPL iterator object implicitly calls the inner iterator giving us all the SPL goodness in memory savings. Isn't that what garbage collection is for? -- Larry Garfield AIM: LOLG42 [EMAIL PROTECTED] ICQ: 6817012 If nature has made any one thing less susceptible than all others of exclusive property, it is the action of the thinking power called an idea, which an individual may exclusively possess as long as he keeps it to himself; but the moment it is divulged, it forces itself into the possession of every one, and the receiver cannot dispossess himself of it. -- Thomas Jefferson -- PHP General Mailing List (http://www.php.net/) To unsubscribe, visit: http://www.php.net/unsub.php
Re: [PHP] RecursiveArrayIterator
On 7/23/07, Larry Garfield [EMAIL PROTECTED] wrote: Isn't that what garbage collection is for? well garbage collection will remove the copy of an array created by foreach, but what Kevin is saying is Iterators dont bother creating a copy of the array, which overall results in memory savings. -nathan On 7/23/07, Larry Garfield [EMAIL PROTECTED] wrote: On Monday 23 July 2007, Kevin Waterson wrote: This one time, at band camp, Jim Lucas [EMAIL PROTECTED] wrote: I don't get it, why not do this? foreach ( $array AS $row ) { foreach ( $row AS $k = $v ) { if ( ! is_array($v) ) { echo {$k} -- {$v}br/\n; } } } Maybe I am missing the point... ??? Indeed, whilst your method is simplistic it leaves many copies of the array dangling in memory. Every time you call foreach it creates a copy of the array internally. SPL iterators do things differently and know only one element at a time. More can be seen at http://phpro.org/tutorials/Introduction-to-SPL.html so the final solution was using a foreach, however, using a foreach on an SPL iterator object implicitly calls the inner iterator giving us all the SPL goodness in memory savings. Isn't that what garbage collection is for? -- Larry Garfield AIM: LOLG42 [EMAIL PROTECTED] ICQ: 6817012 If nature has made any one thing less susceptible than all others of exclusive property, it is the action of the thinking power called an idea, which an individual may exclusively possess as long as he keeps it to himself; but the moment it is divulged, it forces itself into the possession of every one, and the receiver cannot dispossess himself of it. -- Thomas Jefferson -- PHP General Mailing List (http://www.php.net/) To unsubscribe, visit: http://www.php.net/unsub.php
Re: [PHP] RecursiveArrayIterator
On Mon, 2007-07-23 at 10:39 -0400, Nathan Nobbe wrote: On 7/23/07, Larry Garfield [EMAIL PROTECTED] wrote: Isn't that what garbage collection is for? well garbage collection will remove the copy of an array created by foreach, but what Kevin is saying is Iterators dont bother creating a copy of the array, which overall results in memory savings. Foreach doesn't bother creating a copy of the array either. It create COW handle. This wasn't true for objects in PHP4 but you're talking about arrays and if you're using iterators then you're also talking about PHP5 so no copy is being used. I don't know for certain, but I'd guess that Iterators are slower than foreach. Slower, but more convenient for some datatypes. Why do I think slower? Because if I'm not mistaken it invokes a userspace function/method on each iteration whereas foreach does not... don't quote me though, I don't use iterators since I write backward compatible scripts and so I haven't bothered to actually look at them. Cheers, Rob. -- ... SwarmBuy.com - http://www.swarmbuy.com Leveraging the buying power of the masses! ... -- PHP General Mailing List (http://www.php.net/) To unsubscribe, visit: http://www.php.net/unsub.php
[PHP] RecursiveArrayIterator
When I run the code below, I get an output of the array which is good. But the first member of the array output is 0=Array. Is there a way to prevent this? eg: 0 -- Array name -- butch sex -- m breed -- boxer name -- fido sex -- m breed -- doberman name -- girly sex -- f breed -- poodle ?php $array = array( array('name'='butch', 'sex'='m', 'breed'='boxer'), array('name'='fido', 'sex'='m', 'breed'='doberman'), array('name'='girly','sex'='f', 'breed'='poodle') ); $iterator = new RecursiveIteratorIterator(new RecursiveArrayIterator($array)); while($iterator-valid()) { echo $iterator-key().' -- '.$iterator-current().'br/'; $iterator-next(); } ? Kind regards Kevin -- Democracy is two wolves and a lamb voting on what to have for lunch. Liberty is a well-armed lamb contesting the vote. -- PHP General Mailing List (http://www.php.net/) To unsubscribe, visit: http://www.php.net/unsub.php
Re: [PHP] RecursiveArrayIterator
Kevin, im not sure why you need the RecursiveIteratorIterator; the RecursiveArrayIterator is capable of handling the nested arrays by itself. here is a revision of the code you posted, using PHP_EOL for newlines since i developed this via the CLI. ?php $array = array( array('name'='butch', 'sex'='m', 'breed'='boxer'), array('name'='fido', 'sex'='m', 'breed'='doberman'), array('name'='girly','sex'='f', 'breed'='poodle') ); $iterator = new RecursiveArrayIterator($array); printArrayKeysRecursively($iterator); function printArrayKeysRecursively(RecursiveArrayIterator $theRecursiveArrayIterator) { while($theRecursiveArrayIterator-valid()) { /// handle the current node if($theRecursiveArrayIterator-hasChildren()) { // determine if the algorithm should recurse to a child $innerRecursiveArrayIterator = $theRecursiveArrayIterator-getChildren(); printArrayKeysRecursively($innerRecursiveArrayIterator); // handle printing of children } else { // print current node echo $theRecursiveArrayIterator-key() . ' = ' . $theRecursiveArrayIterator-current() . PHP_EOL; } $theRecursiveArrayIterator-next(); // move to the next node } } ? here is the output on my box: [EMAIL PROTECTED] ~ $ php testRecursiveIterator.php name = butch sex = m breed = boxer name = fido sex = m breed = doberman name = girly sex = f breed = poodle - nathan On 7/22/07, Kevin Waterson [EMAIL PROTECTED] wrote: When I run the code below, I get an output of the array which is good. But the first member of the array output is 0=Array. Is there a way to prevent this? eg: 0 -- Array name -- butch sex -- m breed -- boxer name -- fido sex -- m breed -- doberman name -- girly sex -- f breed -- poodle ?php $array = array( array('name'='butch', 'sex'='m', 'breed'='boxer'), array('name'='fido', 'sex'='m', 'breed'='doberman'), array('name'='girly','sex'='f', 'breed'='poodle') ); $iterator = new RecursiveIteratorIterator(new RecursiveArrayIterator($array)); while($iterator-valid()) { echo $iterator-key().' -- '.$iterator-current().'br/'; $iterator-next(); } ? Kind regards Kevin -- Democracy is two wolves and a lamb voting on what to have for lunch. Liberty is a well-armed lamb contesting the vote. -- PHP General Mailing List (http://www.php.net/) To unsubscribe, visit: http://www.php.net/unsub.php
Re: [PHP] RecursiveArrayIterator
This one time, at band camp, Nathan Nobbe [EMAIL PROTECTED] wrote: Thanks for the response. I was hoping to avoid this sort of recursion within userspace and keep it at a lower level. Should not the recursive iterator recurse so we dont need to be using user defined functions? printArrayKeysRecursively($innerRecursiveArrayIterator); // handle printing Kind regards Kevin -- Democracy is two wolves and a lamb voting on what to have for lunch. Liberty is a well-armed lamb contesting the vote. -- PHP General Mailing List (http://www.php.net/) To unsubscribe, visit: http://www.php.net/unsub.php
Re: [PHP] RecursiveArrayIterator
This is what I have so far.. ?php $array = array( array('name'='butch', 'sex'='m', 'breed'='boxer'), array('name'='fido', 'sex'='m', 'breed'='doberman'), array('name'='girly','sex'='f', 'breed'='poodle') ); $iterator = new RecursiveIteratorIterator(new RecursiveArrayIterator($array)); while($iterator-valid()) { if(!$iterator-hasChildren()) { echo $iterator-key().' -- '.$iterator-current().'br/'; } $iterator-next(); } ? Kevin -- Democracy is two wolves and a lamb voting on what to have for lunch. Liberty is a well-armed lamb contesting the vote. -- PHP General Mailing List (http://www.php.net/) To unsubscribe, visit: http://www.php.net/unsub.php
Re: [PHP] RecursiveArrayIterator
there is no base case in the printArrayKeysRecursively method; therefore it is not handling recursion; its just using the RecursiveArrayItereators public methods. i think that is totally appropriate. but i believe i understand what youre getting at; namely the RecursiveArrayIterator implments Iterator, sooo, we should be able to use the foreach construct in our client code to cleanly iterate over the object. here is a new revision, which you may like more than the first one: ?php $array = array( array('name'='butch', 'sex'='m', 'breed'='boxer'), array('name'='fido', 'sex'='m', 'breed'='doberman'), array('name'='girly','sex'='f', 'breed'='poodle') ); $iterator = new RecursiveArrayIterator($array); foreach($iterator as $outerValue) { foreach($outerValue as $innerKey = $innerValue) { echo $innerKey . ' = ' . $innerValue . PHP_EOL; } } ? notice that there are 2 foreach invocations; those correspond directly to the levels of nesting in $array. so if you had another level of nesting in $array, there would have to be another level of nesting in the foreach invocations (if you want to do something w/ those values). that brings us to RecursiveIteratorIterator which quoting Harry Fuecks in his article on SPLhttp://www.sitepoint.com/article/php5-standard-library *RecursiveIteratorIterator: this helps you do cool stuff like flatten a hierarchical data structure so that you can loop through it with a single foreach statement, while still preserving knowledge of the hierarchy. This class could be very useful for rendering tree menus, for example. *as i understand it RecursiveIteratorIterator essentially allows you to define a particular action depending on which level of children is currently being operated on. so i think the decision to use that over RecursiveArrayIterator comes down to the number of levels of nesting that will be in your data structure. if it will always be 2 levels (or a static number of levels that is relatively small), stick w/ RecursiveArrayIterator, otherwise if the number of nested levels is going to vary (or be more than a few), i think, thats when you need to consider RecursiveIteratorIterator. -nathan note: im still a newb on spl myself :) On 7/22/07, Kevin Waterson [EMAIL PROTECTED] wrote: This one time, at band camp, Nathan Nobbe [EMAIL PROTECTED] wrote: Thanks for the response. I was hoping to avoid this sort of recursion within userspace and keep it at a lower level. Should not the recursive iterator recurse so we dont need to be using user defined functions? printArrayKeysRecursively($innerRecursiveArrayIterator); // handle printing Kind regards Kevin -- Democracy is two wolves and a lamb voting on what to have for lunch. Liberty is a well-armed lamb contesting the vote. -- PHP General Mailing List (http://www.php.net/) To unsubscribe, visit: http://www.php.net/unsub.php
Re: [PHP] RecursiveArrayIterator
Kevin Waterson wrote: This is what I have so far.. ?php $array = array( array('name'='butch', 'sex'='m', 'breed'='boxer'), array('name'='fido', 'sex'='m', 'breed'='doberman'), array('name'='girly','sex'='f', 'breed'='poodle') ); $iterator = new RecursiveIteratorIterator(new RecursiveArrayIterator($array)); while($iterator-valid()) { if(!$iterator-hasChildren()) { echo $iterator-key().' -- '.$iterator-current().'br/'; } $iterator-next(); } ? Kevin I don't get it, why not do this? ?php $array = array( array('name'='butch', 'sex'='m', 'breed'='boxer'), array('name'='fido', 'sex'='m', 'breed'='doberman'), array('name'='girly','sex'='f', 'breed'='poodle') ); foreach ( $array AS $row ) { foreach ( $row AS $k = $v ) { if ( ! is_array($v) ) { echo {$k} -- {$v}br/\n; } } } ? This seems like a few less lines of code Maybe I am missing the point... ??? Jim Lucas -- PHP General Mailing List (http://www.php.net/) To unsubscribe, visit: http://www.php.net/unsub.php