tags:

views:

381

answers:

3

Try as I might I cannot get my head around what the IteratorIterator class actually does. I understand that classes can implement Traversable so the engine knows it can loop using foreach and I realise that IteratorIterator is supposed to convert anything that is Traversable into an Iterator but I cannot for the life of me understand how.

Take for example, the PDOStatement class; how would the standard Iterator methods (next, key, rewind, etc) be implemented to allow iteration over a PDOStatement?

Sorry if my question is unclear, I am just struggling to grasp the exact reason for this class and the documentation on it is scant.

Thanks,

Will

Update: Going through the phpt files, I found one test which uses IteratorIterator:

<?php

$root = simplexml_load_string('<?xml version="1.0"?>
<root>
    <child>Hello</child>
    <child>World</child>
</root>
');

foreach (new IteratorIterator($root->child) as $child) {
    echo $child."\n";
}

?>

The expected output is:

Hello
World

I don't really follow how the IteratorIterator construct takes $root->child as an argument and how it manages to iterate over the child elements.

A: 

i thought example #2 here is quite straight forward...
it basically lets you implement a specific behavior for your class for the next/previous/current/rewind/key array functions, expected by the php foreach parser.

so for implementing your question, one would create an Iterator class with an PDOStatement as its memeber, than for example use the next method to call the PDOStatement::fetch to return its next statement. storing it will let you implement both perivous and current. havn't used this class too much but i bet it isn't that hard o implement a rewind and key. note that this is on the fly so i might be wrong on the details, but i think the concept should be clear

XiroX
I'm not sure I follow. The example you linked to talks about a standard Iterator not the IteratorIterator class (http://us2.php.net/manual/en/class.iteratoriterator.php). Could you please clarify?
WilliamMartin
A: 

Based on this, I think it allows you to Iterate over Iterated objects. I.e. you can pull other objects in your master object and using IteratorIterator on your master object, Iterate the child objects as well.

UPDATE: Based on your update. This makes sense to me, though there is only one root object, so iterating it doesn't really apply in this example, but you could if there were more root objects. In other words, I believe IteratorIterator is the same as having nested foreach loops, without having to know all of the elements of each object. In other words, a nested foreach using object oriented objects... there's a redundant statement. :-)

Scott Lundberg
A: 

If you didnt find it yet, http://www.phpro.org/tutorials/Introduction-to-SPL.html has a few examples that might help you.


IteratorIterator >

  • "This iterator wrapper allows the conversion of anything that is Traversable into an Iterator."

Traversable >

  • "Interface to detect if a class is traversable using foreach."
  • "Internal (built-in) classes that implement this interface can be used in a foreach construct and do not need to implement IteratorAggregate or Iterator."
  • "This is an internal engine interface which cannot be implemented in PHP scripts. Either IteratorAggregate or Iterator must be used instead."

The site has some RecursiveIteratorIterator examples that might be handy but, if i get it right, IteratorIterator is from the scripting point of view pretty useless (when used to foreach at least).

It creates Iterateable Objects out of Objects implementing the Traversable interface, but intern classes implementing the Traversable interface are foreachable anyway and scripts cannot implement Traversable...

(Not mentioned in the docs, the SimpleXMLElement is implementing Traversable)

Kuchen