HomePHP Page 4 - Iterators in the Simplest Sense: An Accessible Implementation in PHP 4
Deriving subclasses from the base Iterator: building an array Iterator class - PHP
In this first article of a series, Alejandro Gervasio explains the core concepts of Iterators in PHP, concentrating most of his efforts on the subject’s practical side.
After defining the base “Iterator” class that I explained in the previous section, the process of creating an array iterator class is really straightforward. The whole task is reduced to deriving a subclass from this parent class, as shown below:
// 'ArrayIterator' subclass class ArrayIterator extends Iterator{ var $data=array(); function ArrayIterator($data=array()){ if(!is_array($data)){ trigger_error('Data must be an array',E_USER_ERROR); } $this->data=$data; } // concrete implementation for 'current()' method function current(){ if(!$data=current($this->data)){ trigger_error('Error retrieving current element',E_USER_ERROR); } return $data; } // concrete implementation for 'prev()' method function prev(){ if(!$data=prev($this->data)){ trigger_error('Error retrieving previous element',E_USER_ERROR); } return $data; } // concrete implementation for 'next()' method function next(){ if(!$data=next($this->data)){ trigger_error('Error retrieving next element',E_USER_ERROR); } return $data; } // concrete implementation for 'end()' method function end(){ if(!$data=end($this->data)){ trigger_error('Error retrieving last element',E_USER_ERROR); } return $data; } // concrete implementation for 'reset()' method function reset(){ if(!$data=reset($this->data)){ trigger_error('Error retrieving first element',E_USER_ERROR); } return $data; } // concrete implementation for 'seek()' method function seek($pos){ if(!is_int($pos)&&$pos<0){ trigger_error('Invalid offset',E_USER_ERROR); } if(!$data=$this->data[$pos]){ trigger_error('Error seeking element',E_USER_ERROR); } return $data; } // concrete implementation for 'count()' method function count(){ if(!$data=count($this->data)){ trigger_error('Error counting elements',E_USER_ERROR); } return $data; } }
Now, you’ll agree I did something useful with the base Iterator class you saw earlier. As you can see, I derived a subclass and created a functional array iterator class, by coding an explicit definition for each of the generic methods of the base class. Not rocket science, right?
In addition, here’s a simple snippet that shows a concrete application for this sample array iterator. Take a look:
$testarray=array('Element1','Element2','Element3','Element4'); $aIterator=&new ArrayIterator($testarray); // display first array element echo $aIterator->reset(); // display current array element echo $aIterator->current(); // display next array element echo $aIterator->next(); // display final array element echo $aIterator->end(); // display previous array element echo $aIterator->prev(); // count array elements echo $aIterator->count(); // seek array element echo $aIterator->seek(2);
Notice how each one of the corresponding methods has been written, in order to allow traversing easily any array passed as an argument to the class constructor. In addition, it’s also possible to count the number of elements within the array, or search a specific element in the structure, by using the “count()” and “seek()” methods respectively.
At this stage, I hope you learned the basic theory of Iterators in PHP, along with an understandable-–yet useful--concrete implementation: the development of an array iterator. However, admittedly an array iterator isn’t a very useful thing on its own, and should be integrated as a building block for more complex applications. But in fact, I’m getting ahead of myself, so please be patient and read the concluding thoughts.
Bottom line
In this first article of the series, I’ve explained the core concepts of Iterators in PHP, concentrating most of my efforts on the subject’s practical side. As you’ve seen in this tutorial, an array iterator is a powerful structure that can be used to step up to building the logic of larger PHP applications.
Keeping this idea in mind, in the next article I’ll show you how to use this array iterator for creating a couple of useful applications, handy for traversing flat files and MySQL result sets. You don’t have any excuses to miss it!