├── .gitignore
├── examples
├── Car.php
├── fraggles.php
├── MyCar.php
├── test.php
├── southParkCharacters.php
├── states.php
└── data.html
├── app
├── Iterators
│ ├── Classes
│ │ ├── CustomArrayIterator.php
│ │ ├── CustomCachingIterator.php
│ │ ├── FizzBuzzFilter.php
│ │ ├── DwarfIterator.php
│ │ ├── Miata.php
│ │ ├── FizzBuzz.php
│ │ ├── OuterIteratorDemo.php
│ │ ├── PrettyBits.php
│ │ ├── SeekableIterator.php
│ │ └── IteratorDemo.php
│ └── Command
│ │ ├── BitMathCommand.php
│ │ ├── RecursiveCommand.php
│ │ ├── SeekCommand.php
│ │ ├── FizzBuzzCommand.php
│ │ ├── IteratorInterfaceCommand.php
│ │ ├── OuterIteratorCommand.php
│ │ ├── FizzBuzzFilteredCommand.html
│ │ ├── FizzBuzzFilteredCommand.php
│ │ ├── ArrayIteratorCommand.php
│ │ ├── GeneratorCommand.php
│ │ ├── DirectoryCommand.php
│ │ └── CachingIteratorCommand.php
├── test.php
└── console.sh
├── README.md
├── composer.json
└── LICENSE
/.gitignore:
--------------------------------------------------------------------------------
1 | composer.lock
2 | vendor/
--------------------------------------------------------------------------------
/examples/Car.php:
--------------------------------------------------------------------------------
1 | key() . ' - ' . $this->current();
10 | }
11 |
12 | }
13 |
--------------------------------------------------------------------------------
/app/Iterators/Classes/CustomCachingIterator.php:
--------------------------------------------------------------------------------
1 | offsetUnset(4);
11 |
12 | return;
13 | }
14 |
15 | }
16 |
--------------------------------------------------------------------------------
/README.md:
--------------------------------------------------------------------------------
1 | # iterators
2 |
3 | This is the sourcecode respository for [Iterating PHP Iterators](https://leanpub.com/iteratingphpiterators) by [Cal Evans](http://blog.calevans.com)
4 |
5 | Copyright: 2015 [E.I.C.C., Inc.](http://eicc.com)
6 |
7 | License: [MIT](http://opensource.org/licenses/MIT)
8 |
9 |
10 |
--------------------------------------------------------------------------------
/app/Iterators/Classes/FizzBuzzFilter.php:
--------------------------------------------------------------------------------
1 | rewind();
11 | $it[3] = 'Cal';
12 | echo "The fourth letter of the alphabet is: " . $it[3] . PHP_EOL;
13 |
14 | print_r($it);
15 |
16 | echo "\n\n";
17 |
18 | print_r($it->getInnerIterator());
19 |
--------------------------------------------------------------------------------
/app/Iterators/Classes/DwarfIterator.php:
--------------------------------------------------------------------------------
1 | filter = $filter;
12 | return;
13 | }
14 |
15 | public function accept()
16 | {
17 | return (strpos($this->getInnerIterator()->current(), $this->filter) !== false);
18 | }
19 |
20 | }
--------------------------------------------------------------------------------
/examples/fraggles.php:
--------------------------------------------------------------------------------
1 | $value) {
23 | echo $key . ":" . $value . "\n";
24 | }
25 | echo "\nDone\n";
26 | die();
27 |
28 |
--------------------------------------------------------------------------------
/examples/test.php:
--------------------------------------------------------------------------------
1 | 'Grumpy',
4 | 2 => 'Happy',
5 | 3 => 'Sleepy',
6 | 4 => 'Bashful',
7 | 5 => 'Sneezy',
8 | 6 => 'Dopey',
9 | 7 => 'Doc'
10 | ];
11 |
12 | $it = new CachingIterator(new ArrayIterator($dwarves),
13 | CachingIterator::FULL_CACHE);
14 | foreach ($it as $v) {
15 | ;
16 | }
17 |
18 | $it->offsetUnset(4);
19 | $it->offsetSet('Cal', 'Kathy');
20 | $it[5] = 'Surly';
21 |
22 | foreach ($it as $offset => $value) {
23 | echo 'Original: ' . $offset . ' == ' . $value . "\n";
24 | }
25 |
26 | foreach ($it->getCache() as $offset => $value) {
27 | echo 'Cache: ' . $offset . ' == ' . $value . "\n";
28 | }
29 |
30 |
--------------------------------------------------------------------------------
/app/console.sh:
--------------------------------------------------------------------------------
1 | #!/usr/bin/env php
2 | addCommands([new Command\ArrayIteratorCommand(),
11 | new Command\CachingIteratorCommand(),
12 | new Command\FizzBuzzCommand(),
13 | new Command\FizzBuzzFilteredCommand(),
14 | new Command\IteratorInterfaceCommand(),
15 | new Command\GeneratorCommand(),
16 | new Command\OuterIteratorCommand(),
17 | new Command\DirectoryCommand(),
18 | new Command\BitMathCommand(),
19 | new Command\SeekCommand]);
20 | $app->run();
--------------------------------------------------------------------------------
/app/Iterators/Classes/Miata.php:
--------------------------------------------------------------------------------
1 | data[$key])) {
20 | $this->data[$key] = $value;
21 | }
22 | return;
23 | }
24 |
25 | public function offsetExists($key)
26 | {
27 | return isset($this->data[$key]);
28 | }
29 |
30 | public function offsetUnset($key)
31 | {
32 | unset($this->data[$key]);
33 | }
34 |
35 | public function offsetGet($key)
36 | {
37 | return isset($this->data[$key]) ? $this->data[$key] : null;
38 | }
39 |
40 | }
--------------------------------------------------------------------------------
/LICENSE:
--------------------------------------------------------------------------------
1 | The MIT License (MIT)
2 |
3 | Copyright (c) 2015 Cal Evans
4 |
5 | Permission is hereby granted, free of charge, to any person obtaining a copy
6 | of this software and associated documentation files (the "Software"), to deal
7 | in the Software without restriction, including without limitation the rights
8 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
9 | copies of the Software, and to permit persons to whom the Software is
10 | furnished to do so, subject to the following conditions:
11 |
12 | The above copyright notice and this permission notice shall be included in all
13 | copies or substantial portions of the Software.
14 |
15 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
18 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
20 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
21 | SOFTWARE.
22 |
23 |
--------------------------------------------------------------------------------
/app/Iterators/Classes/FizzBuzz.php:
--------------------------------------------------------------------------------
1 | numbers = $numbers;
12 | return;
13 | }
14 |
15 | public function current()
16 | {
17 | $returnValue = '';
18 | $returnValue .= ($this->numbers[$this->pointer] % 3 === 0 ? 'Fizz' : '');
19 | $returnValue .= ($this->numbers[$this->pointer] % 5 === 0 ? 'Buzz' : '');
20 | $returnValue = (empty($returnValue) ? $this->numbers[$this->pointer] : $returnValue);
21 | return $returnValue;
22 | }
23 |
24 | public function key()
25 | {
26 | return $this->pointer;
27 | }
28 |
29 |
30 | public function next()
31 | {
32 | $this->pointer++;
33 | return;
34 | }
35 |
36 |
37 | public function rewind()
38 | {
39 | $this->pointer = 0;
40 | return;
41 | }
42 |
43 |
44 | public function valid()
45 | {
46 | return isset($this->numbers[$this->pointer]);
47 | }
48 |
49 | }
--------------------------------------------------------------------------------
/app/Iterators/Classes/OuterIteratorDemo.php:
--------------------------------------------------------------------------------
1 | numbers = $numbers;
12 | return;
13 | }
14 |
15 | public function current()
16 | {
17 | $returnValue = '';
18 | $returnValue .= ($this->numbers[$this->pointer] % 3 === 0 ? 'Fizz' : '');
19 | $returnValue .= ($this->numbers[$this->pointer] % 5 === 0 ? 'Buzz' : '');
20 | $returnValue = (empty($returnValue) ? $this->numbers[$this->pointer] : $returnValue);
21 | return $returnValue;
22 | }
23 |
24 | public function key()
25 | {
26 | return $this->pointer;
27 | }
28 |
29 |
30 | public function next()
31 | {
32 | $this->pointer++;
33 | return;
34 | }
35 |
36 |
37 | public function rewind()
38 | {
39 | $this->pointer = 0;
40 | return;
41 | }
42 |
43 |
44 | public function valid()
45 | {
46 | return isset($this->numbers[$this->pointer]);
47 | }
48 |
49 | }
--------------------------------------------------------------------------------
/app/Iterators/Command/BitMathCommand.php:
--------------------------------------------------------------------------------
1 | setName("bitmath")
20 | ->setDescription("Displays a 14 bit integer as individual flags")
21 | ->setDefinition($definition)
22 | ->setHelp("Quick demonstration of how bitmath works. ");
23 | }
24 |
25 |
26 | protected function execute(
27 | InputInterface $input,
28 | OutputInterface $output
29 | ) {
30 | $number = (int)$input->getOption('number');
31 |
32 | PrettyBits::printIt($number);
33 |
34 | $output->writeln("Done");
35 | return;
36 | }
37 |
38 | }
--------------------------------------------------------------------------------
/examples/southParkCharacters.php:
--------------------------------------------------------------------------------
1 | setName("recursive")
15 | ->setDescription("Demonstrate a Recrusive Iterator")
16 | ->setHelp("Iterate over a multi-dimensional array using ther RecursiveIteratorIterator");
17 | }
18 |
19 |
20 | protected function execute(
21 | InputInterface $input,
22 | OutputInterface $output
23 | ) {
24 | $characters = include __DIR__ . '/../../../examples/southparkCharacters.php';
25 |
26 | $output->writeln("Source Array:");
27 | print_r($characters);
28 |
29 | $output->writeln("Iterator Output");
30 | $iterator = new \RecursiveIteratorIterator(new \RecursiveArrayIterator($characters));
31 |
32 | foreach ($iterator as $key => $value) {
33 | $output->writeln($key . " : " . $value);;
34 | }
35 |
36 | $output->writeln("Done");
37 | return;
38 |
39 | }
40 |
41 | }
42 |
43 |
--------------------------------------------------------------------------------
/app/Iterators/Command/SeekCommand.php:
--------------------------------------------------------------------------------
1 | setName("seek")
16 | ->setDescription("Demonstrate PHP's SeekIterator")
17 | ->setHelp("Runs a simple demo to show how to use PHP's SeekIterator.");
18 | }
19 |
20 |
21 | protected function execute(
22 | InputInterface $input,
23 | OutputInterface $output
24 | ) {
25 | $fraggles = include __DIR__ . '/../../../examples/fraggles.php';
26 |
27 | $fraggleIterator = new SeekableIterator($fraggles, false);
28 |
29 | /*
30 | * This will nt produce the results you expect.
31 | */
32 | for ($lcvA = 0; $lcvA < count($fraggleIterator); $lcvA++) {
33 | $fraggleIterator->seek($lcvA);
34 | echo $lcvA . " : " . $fraggleIterator->current() . "\n";
35 | }
36 |
37 | $output->writeln("Done");
38 | return;
39 |
40 | }
41 |
42 | }
43 |
44 |
--------------------------------------------------------------------------------
/app/Iterators/Command/FizzBuzzCommand.php:
--------------------------------------------------------------------------------
1 | setName("fizzbuzz")
20 | ->setDescription("Outputs FizzBuzz")
21 | ->setDefinition($definition)
22 | ->setHelp("Simple demonstration of how to modify the output of an Iterator.");
23 | }
24 |
25 |
26 | protected function execute(
27 | InputInterface $input,
28 | OutputInterface $output
29 | ) {
30 | $max = max((int)$input->getOption('max'), 1);
31 | $numbers = range(1, $max);
32 |
33 | $fizzBuzz = new FizzBuzz($numbers);
34 |
35 | foreach ($fizzBuzz as $thisNumber) {
36 | $output->writeln(" " . $thisNumber);
37 | } // foreach($iteratableClass as $committer)
38 |
39 | $output->writeln("Done");
40 | return;
41 | }
42 |
43 | }
--------------------------------------------------------------------------------
/app/Iterators/Command/IteratorInterfaceCommand.php:
--------------------------------------------------------------------------------
1 | setName("iteratorInterface")
15 | ->setDescription("Shows a list of the recent committers to PHP")
16 | ->setHelp("Demonstrates building a custom Iterator using PHP's built in IteratorInterface");
17 | }
18 |
19 |
20 | protected function execute(
21 | InputInterface $input,
22 | OutputInterface $output
23 | ) {
24 | $iteratableClass = new IteratorDemo();
25 |
26 | if ($output->getVerbosity() >= OutputInterface::VERBOSITY_VERBOSE) {
27 | $iteratableClass->setVerbose(true);
28 | }
29 |
30 | $output->writeln("Looks like we've got " . count($iteratableClass) . " recent committers.");
31 |
32 | foreach ($iteratableClass as $committer) {
33 | $output->writeln(" Commiter : " . $committer['name'] . ' from ' . $committer['location']);
34 | } // foreach($iteratableClass as $committer)
35 |
36 | $output->writeln("Done");
37 | return;
38 | }
39 |
40 | }
--------------------------------------------------------------------------------
/app/Iterators/Command/OuterIteratorCommand.php:
--------------------------------------------------------------------------------
1 | setName("outerIterator")
18 | ->setDescription("Filters the Seven Dwarfs")
19 | ->setDefinition($definition)
20 | ->setHelp("Demonstrates how an Outer Iterator works.");
21 | }
22 |
23 |
24 | protected function execute(
25 | InputInterface $input,
26 | OutputInterface $output
27 | ) {
28 | $filter = substr((string)$input->getOption('filter'), 0, 1);
29 | $dwarves = ['Grumpy ', 'Happy ', 'Sleepy ', 'Bashful ', 'Sneezy ', 'Dopey ', 'Doc '];
30 | $dwarfIterator = new DwarfIterator(new \ArrayIterator($dwarves), $filter);
31 |
32 | foreach ($dwarfIterator as $thisDwarf) {
33 | $output->writeln($thisDwarf);
34 | } // foreach($dwarfIterator as $thisDwarf)
35 |
36 | $output->writeln("Done");
37 | return;
38 | }
39 |
40 | }
--------------------------------------------------------------------------------
/examples/states.php:
--------------------------------------------------------------------------------
1 | 'Alabama',
4 | 'AK' => 'Alaska',
5 | 'AZ' => 'Arizona',
6 | 'AR' => 'Arkansas',
7 | 'CA' => 'California',
8 | 'CO' => 'Colorado',
9 | 'CT' => 'Connecticut',
10 | 'DE' => 'Delaware',
11 | 'FL' => 'Florida',
12 | 'GA' => 'Georgia',
13 | 'HI' => 'Hawaii',
14 | 'ID' => 'Idaho',
15 | 'IL' => 'Illinois',
16 | 'IN' => 'Indiana',
17 | 'IA' => 'Iowa',
18 | 'KS' => 'Kansas',
19 | 'KY' => 'Kentucky',
20 | 'LA' => 'Louisiana',
21 | 'ME' => 'Maine',
22 | 'MD' => 'Maryland',
23 | 'MA' => 'Massachusetts',
24 | 'MI' => 'Michigan',
25 | 'MN' => 'Minnesota',
26 | 'MS' => 'Mississippi',
27 | 'MO' => 'Missouri',
28 | 'MT' => 'Montana',
29 | 'NE' => 'Nebraska',
30 | 'NV' => 'Nevada',
31 | 'NH' => 'New Hampshire',
32 | 'NJ' => 'New Jersey',
33 | 'NM' => 'New Mexico',
34 | 'NY' => 'New York',
35 | 'NC' => 'North Carolina',
36 | 'ND' => 'North Dakota',
37 | 'OH' => 'Ohio',
38 | 'OK' => 'Oklahoma',
39 | 'OR' => 'Oregon',
40 | 'PA' => 'Pennsylvania',
41 | 'RI' => 'Rhode Island',
42 | 'SC' => 'South Carolina',
43 | 'SD' => 'South Dakota',
44 | 'TN' => 'Tennessee',
45 | 'TX' => 'Texas',
46 | 'UT' => 'Utah',
47 | 'VT' => 'Vermont',
48 | 'VA' => 'Virginia',
49 | 'WA' => 'Washington',
50 | 'WV' => 'West Virginia',
51 | 'WI' => 'Wisconsin',
52 | 'WY' => 'Wyoming'
53 | ];
54 |
--------------------------------------------------------------------------------
/app/Iterators/Command/FizzBuzzFilteredCommand.html:
--------------------------------------------------------------------------------
1 | setName("fizzbuzzfiltered")
20 | ->setDescription("Filters input before outputting FizzBuzz")
21 | ->setDefinition($definition)
22 | ->setHelp("Simple demonstration of how to modify the input and output of an Iterator.");
23 | }
24 |
25 |
26 | protected function execute(InputInterface $input,
27 | OutputInterface $output)
28 | {
29 | $max = (int)$input->getOption('max');
30 | $numbers = range(1, $max);
31 |
32 | $fizzBuzzFiltered = new \Iterators\Classes\FizzBuzzFilter($numbers);
33 |
34 | foreach($numbers as $thisNumber) {
35 | $fizzBuzzFiltered[]=$thisNumber;
36 | }
37 |
38 | $fizzBuzz = new \Iterators\Classes\FizzBuzz($fizzBuzzFiltered);
39 |
40 | foreach($fizzBuzz as $thisNumber) {
41 | $output->writeln(" ".$thisNumber);
42 | } // foreach($iteratableClass as $committer)
43 |
44 | $output->writeln("Done");
45 | return;
46 | }
47 |
48 | }
--------------------------------------------------------------------------------
/app/Iterators/Command/FizzBuzzFilteredCommand.php:
--------------------------------------------------------------------------------
1 | setName("fizzbuzzfiltered")
21 | ->setDescription("Filters input before outputting FizzBuzz")
22 | ->setDefinition($definition)
23 | ->setHelp("Simple demonstration of how to modify the input and output of an Iterator.");
24 | }
25 |
26 |
27 | protected function execute(
28 | InputInterface $input,
29 | OutputInterface $output
30 | ) {
31 | $max = max((int)$input->getOption('max'), 1);
32 | $numbers = range(1, $max);
33 |
34 | $fizzBuzzFiltered = new FizzBuzzFilter();
35 |
36 | foreach ($numbers as $thisNumber) {
37 | $fizzBuzzFiltered[] = $thisNumber;
38 | }
39 |
40 | $fizzBuzz = new FizzBuzz($fizzBuzzFiltered);
41 |
42 | foreach ($fizzBuzz as $thisNumber) {
43 | $output->writeln(" " . $thisNumber);
44 | } // foreach($iteratableClass as $committer)
45 |
46 | $output->writeln("Done");
47 | return;
48 | }
49 |
50 | }
--------------------------------------------------------------------------------
/app/Iterators/Command/ArrayIteratorCommand.php:
--------------------------------------------------------------------------------
1 | setName("arrayIterator")
15 | ->setDescription("Does something clever.")
16 | ->setHelp("Demonstrates the use of PHP's built-in ArrayIterator");
17 | }
18 |
19 |
20 | protected function execute(
21 | InputInterface $input,
22 | OutputInterface $output
23 | ) {
24 | $fraggles = include __DIR__ . '/../../../examples/fraggles.php';
25 | $arrayIterator = new \ArrayIterator($fraggles);
26 |
27 | // Print the array
28 | $output->writeln("The array in natural order");
29 | foreach ($arrayIterator as $thisFraggle) {
30 | $output->writeln(" " . $thisFraggle);
31 | }
32 |
33 | // print the array sorted
34 | $output->writeln("The array in alphabetical order");
35 | $arrayIterator->asort();
36 | foreach ($arrayIterator as $thisFraggle) {
37 | $output->writeln(" " . $thisFraggle);
38 | }
39 |
40 |
41 | // print the array sorted
42 | $output->writeln("Emprorer First order");
43 | $arrayIterator->uasort([$this, 'emperorFirst']);
44 |
45 | foreach ($arrayIterator as $thisFraggle) {
46 | $output->writeln(" " . $thisFraggle);
47 | }
48 |
49 |
50 | $output->writeln("Done");
51 | return;
52 | }
53 |
54 | public function emperorFirst($a)
55 | {
56 | return (substr($a, 0, 3) == "Emp" ? 0 : 1);
57 | }
58 | }
--------------------------------------------------------------------------------
/app/Iterators/Classes/SeekableIterator.php:
--------------------------------------------------------------------------------
1 | setVerbose($verbose);
14 | $this->data = $data;
15 | }
16 |
17 |
18 | public function count()
19 | {
20 | if ($this->verbose) {
21 | echo "-- Count\n";
22 | }
23 | return count($this->data);
24 | }
25 |
26 |
27 | public function key()
28 | {
29 | if ($this->verbose) {
30 | echo "-- Key\n";
31 | }
32 | return $this->pointer;
33 | }
34 |
35 |
36 | public function next()
37 | {
38 | if ($this->verbose) {
39 | echo "-- Next\n";
40 | }
41 |
42 | $this->pointer++;
43 |
44 | return;
45 | }
46 |
47 |
48 | public function rewind()
49 | {
50 | if ($this->verbose) {
51 | echo "-- Rewind\n";
52 | }
53 | $this->pointer = 0;
54 |
55 | return;
56 | }
57 |
58 |
59 | public function valid()
60 | {
61 | if ($this->verbose) {
62 | echo "-- Valid\n";
63 | }
64 |
65 | return isset($this->data[$this->pointer]);
66 | }
67 |
68 |
69 | public function current()
70 | {
71 | if ($this->verbose) {
72 | echo "-- Current\n";
73 | }
74 | return $this->data[$this->pointer];
75 | }
76 |
77 |
78 | public function seek($position)
79 | {
80 |
81 | $position = rand(0, count($this->data) - 1);
82 |
83 | if (!isset($this->data[$position])) {
84 | throw new \OutOfBoundsException("invalid seek position ($position)");
85 | }
86 |
87 | $this->pointer = $position;
88 |
89 | return;
90 | }
91 |
92 | /*
93 | * Not part of the Seekable interface
94 | */
95 | public function setVerbose($newValue = false)
96 | {
97 | $this->verbose = (bool)$newValue;
98 | return;
99 | }
100 |
101 | }
--------------------------------------------------------------------------------
/app/Iterators/Command/GeneratorCommand.php:
--------------------------------------------------------------------------------
1 | setName("generator")
16 | ->setDescription("Use PHP's Generator to output recent contributors to the core.")
17 | ->setHelp("Demonstrates how a Generator works.");
18 | }
19 |
20 |
21 | protected function execute(
22 | InputInterface $input,
23 | OutputInterface $output
24 | ) {
25 | $client = new Client();
26 | $commits = $client->get('https://api.github.com/repos/php/php-src/commits')->json();
27 | $commitGenerator = $this->gatherCommits($commits, $output->getVerbosity());
28 |
29 | /*
30 | * If the verbose flag is passed, prove that generators are an object.
31 | */
32 | if ($output->getVerbosity() === OutputInterface::VERBOSITY_DEBUG) {
33 | print_r($commitGenerator);
34 | print_r(class_implements($commitGenerator));
35 | $output->writeln("Done");
36 | return;
37 | }
38 |
39 | foreach ($commitGenerator as $thisCommit) {
40 | echo $thisCommit['committer']['name'] . " : " . $thisCommit['committer']['location'] . "\n";
41 | }
42 |
43 | $output->writeln("Done");
44 | return;
45 | }
46 |
47 |
48 | protected function gatherCommits($gatheredComits, $verbosity)
49 | {
50 | $committers = [];
51 |
52 | foreach ($gatheredComits as $thisCommit) {
53 |
54 | if (!isset($committers[$thisCommit['author']['id']])) {
55 | $client = new Client();
56 | $committers[$thisCommit['author']['id']] = $client->get('https://api.github.com/user/' . $thisCommit['author']['id'])->json();
57 | }
58 |
59 | $payload = ['commit' => $thisCommit, 'committer' => $committers[$thisCommit['author']['id']]];
60 |
61 | if ($verbosity === OutputInterface::VERBOSITY_VERBOSE) {
62 | echo "Pre Yeild\n";
63 | }
64 |
65 | yield $payload;
66 |
67 | if ($verbosity === OutputInterface::VERBOSITY_VERBOSE) {
68 | echo "Post Yeild\n";
69 | }
70 |
71 | }
72 | }
73 | }
74 |
--------------------------------------------------------------------------------
/app/Iterators/Command/DirectoryCommand.php:
--------------------------------------------------------------------------------
1 | setName("directory")
21 | ->setDescription("Demonstrate PHP's DirectoryIterator")
22 | ->setDefinition($definition)
23 | ->setHelp("Recurse a directory and print out all the files in it and all subdirectories.");
24 |
25 | }
26 |
27 |
28 | protected function execute(
29 | InputInterface $input,
30 | OutputInterface $output
31 | ) {
32 |
33 | $startingPoint = $input->getOption('directory');
34 | $method = (int)$input->getOption('method');
35 |
36 | $output->writeln("Iterating over " . $startingPoint);
37 |
38 | switch ($method) {
39 |
40 | case 1:
41 | $this->method1($startingPoint);
42 | break;
43 |
44 | case 2:
45 | $this->method2($startingPoint);
46 |
47 | }
48 |
49 | $output->writeln("\nDone");
50 | return;
51 |
52 | }
53 |
54 | protected function method1($dir, $padLength = 0)
55 | {
56 | $thisDir = new \DirectoryIterator($dir);
57 |
58 | foreach ($thisDir as $value) {
59 | if ($thisDir->isDot()) {
60 | // Skip the dot directories
61 | continue;
62 | } else {
63 | if ($thisDir->isDir()) {
64 |
65 | if ($thisDir->isReadable()) {
66 | // if this is a new directory AND we have permission to read it, recurse into it.
67 | echo str_repeat(' ', $padLength * 2) . $value . "\\\n";
68 | $this->method1($dir . '/' . $value, $padLength + 1);
69 | }
70 |
71 | } else {
72 | // output the file
73 | echo str_repeat(' ', $padLength * 2) . $value . "\n";
74 | }
75 | }
76 | }
77 | return;
78 | }
79 |
80 |
81 | protected function method2($dir, $padLength = 0)
82 | {
83 |
84 | try {
85 | $thisDir = new \FilesystemIterator($dir);
86 | } catch (\UnexpectedValueException $e) {
87 | return;
88 | }
89 |
90 | foreach ($thisDir as $value) {
91 |
92 | if ($value->isDir()) {
93 | echo str_repeat(' ', $padLength * 2) . $value . "\\\n";
94 | $this->method2($value->getPathname(), $padLength + 1);
95 | }
96 |
97 | echo str_repeat(' ', $padLength * 2) . $value->getPathname() . "\n";
98 | }
99 |
100 | return;
101 | }
102 |
103 |
104 | }
105 |
--------------------------------------------------------------------------------
/app/Iterators/Classes/IteratorDemo.php:
--------------------------------------------------------------------------------
1 | populate();
16 | $this->rewind();
17 | return;
18 | }
19 |
20 |
21 | public function count()
22 | {
23 | if ($this->verbose) {
24 | echo "-- Count\n";
25 | }
26 | return count($this->committers);
27 | }
28 |
29 |
30 | public function key()
31 | {
32 | if ($this->verbose) {
33 | echo "-- Key\n";
34 | }
35 | return $this->pointer;
36 | }
37 |
38 |
39 | public function next()
40 | {
41 | if ($this->verbose) {
42 | echo "-- Next\n";
43 | }
44 | $this->pointer++;
45 | if ($this->valid()) {
46 | $this->committers[$this->pointer]['location'] = $this->fetchLocation($this->pointer);
47 | }
48 |
49 | return;
50 | }
51 |
52 |
53 | public function rewind()
54 | {
55 | if ($this->verbose) {
56 | echo "-- Rewind\n";
57 | }
58 | $this->pointer = 0;
59 |
60 | if (count($this->committers) > 0) {
61 | $this->committers[$this->pointer]['location'] = $this->fetchLocation($this->pointer);
62 | }
63 |
64 | return;
65 | }
66 |
67 |
68 | public function valid()
69 | {
70 | if ($this->verbose) {
71 | echo "-- Valid\n";
72 | }
73 |
74 | return isset($this->committers[$this->pointer]);
75 | }
76 |
77 |
78 | public function current()
79 | {
80 | if ($this->verbose) {
81 | echo "-- Current\n";
82 | }
83 | return $this->committers[$this->pointer];
84 | }
85 |
86 |
87 | /*
88 | * These are not part of the IteratorInterface.
89 | */
90 | protected function checkCommiters($email)
91 | {
92 | if ($this->verbose) {
93 | echo "-- Check Committers\n";
94 | }
95 | $returnValue = false;
96 | foreach ($this->committers as $commiter) {
97 | if ($commiter['email'] === $email) {
98 | $returnValue = true;
99 | break;
100 | }
101 | }
102 |
103 | return $returnValue;
104 |
105 | }
106 |
107 |
108 | protected function populate()
109 | {
110 | if ($this->verbose) {
111 | echo "-- Populate\n";
112 | }
113 |
114 | $client = new Client();
115 | $response = $client->get('https://api.github.com/repos/php/php-src/commits');
116 | $commits = $response->json();
117 |
118 | foreach ($commits as $thisCommit) {
119 | if (!$this->checkCommiters($thisCommit['commit']['author']['email'])) {
120 | $user = [
121 | 'email' => $thisCommit['commit']['author']['email'],
122 | 'name' => $thisCommit['commit']['author']['name']
123 | ];
124 |
125 | if (is_array($thisCommit['author'])) {
126 | $user['id'] = $thisCommit['author']['id'];
127 | }
128 |
129 | $this->committers[] = $user;
130 | }
131 | }
132 | return;
133 | }
134 |
135 |
136 | protected function fetchLocation($pointer)
137 | {
138 | if ($this->verbose) {
139 | echo "-- Fetch Location\n";
140 | }
141 | if (empty($this->committers[$pointer]['id'])) {
142 | return 'Unknown';
143 | }
144 |
145 | if (!isset($this->committers[$pointer]['location'])) {
146 | $client = new Client();
147 | $response = $client->get('https://api.github.com/user/' . $this->committers[$pointer]['id']);
148 | $githubUser = $response->json();
149 | $returnValue = $githubUser['location'];
150 | } else {
151 | $returnValue = $this->committers[$pointer]['location'];
152 | }
153 | return $returnValue;
154 | }
155 |
156 |
157 | public function setVerbose($newValue = false)
158 | {
159 | $this->verbose = (bool)$newValue;
160 | return;
161 | }
162 |
163 | }
--------------------------------------------------------------------------------
/app/Iterators/Command/CachingIteratorCommand.php:
--------------------------------------------------------------------------------
1 | setName("cachingIterator")
17 | ->setDescription("Output the seven dwarfs in CSV format.")
18 | ->setHelp("Demonstrates how a Caching Iterator works.");
19 | }
20 |
21 |
22 | protected function execute(
23 | InputInterface $input,
24 | OutputInterface $output
25 | ) {
26 | $dwarves = [
27 | 1 => 'Grumpy',
28 | 2 => 'Happy',
29 | 3 => 'Sleepy',
30 | 4 => 'Bashful',
31 | 5 => 'Sneezy',
32 | 6 => 'Dopey',
33 | 7 => 'Doc'
34 | ];
35 | $output->writeln('Look ahead exampe. Build a CSV the hard way.');
36 |
37 | $dwarfIterator = new \ArrayIterator($dwarves);
38 | $cachingDwarfIterator = new \CachingIterator($dwarfIterator);
39 | $dwarfListOutput = '';
40 |
41 | foreach ($cachingDwarfIterator as $thisDwarf) {
42 | $dwarfListOutput .= $thisDwarf;
43 |
44 | if ($cachingDwarfIterator->hasNext()) {
45 | $dwarfListOutput .= ',';
46 | }
47 |
48 | } // foreach($dwarfIterator as $thisDwarf)
49 |
50 | $output->writeln($dwarfListOutput);
51 | $output->writeln(' ');
52 |
53 | $dwarfIterator = null;
54 | $cachingDwarfIterator = null;
55 |
56 |
57 | $output->writeln('Set the TOSTRING_USE_KEY flag');
58 | $dwarfIterator = new \ArrayIterator($dwarves);
59 | $cachingDwarfIterator = new \CachingIterator($dwarfIterator, \CachingIterator::TOSTRING_USE_KEY);
60 |
61 | foreach ($cachingDwarfIterator as $key => $thisDwarf) {
62 | var_dump((string)$cachingDwarfIterator);
63 | echo "\n";
64 | } // foreach($dwarfIterator as $thisDwarf)
65 |
66 | $dwarfIterator = null;
67 | $cachingDwarfIterator = null;
68 |
69 | $output->writeln(' ');
70 | $output->writeln('Setting the TOSTRING_USE_CURRENT flag');
71 |
72 | $dwarfIterator = new \ArrayIterator($dwarves);
73 | $cachingDwarfIterator = new \CachingIterator($dwarfIterator, \CachingIterator::TOSTRING_USE_CURRENT);
74 |
75 | foreach ($cachingDwarfIterator as $key => $thisDwarf) {
76 | var_dump((string)$cachingDwarfIterator);
77 | echo "\n";
78 | } // foreach($dwarfIterator as $thisDwarf)
79 |
80 |
81 | $output->writeln(' ');
82 | $output->writeln('Setting the TOSTRING_USE_INNER flag');
83 |
84 | $dwarfIterator = new CustomArrayIterator($dwarves);
85 | $cachingDwarfIterator = new \CachingIterator($dwarfIterator, \CachingIterator::TOSTRING_USE_INNER);
86 |
87 | foreach ($cachingDwarfIterator as $key => $thisDwarf) {
88 | var_dump((string)$cachingDwarfIterator);
89 | echo "\n";
90 | } // foreach($dwarfIterator as $thisDwarf)
91 |
92 |
93 | $output->writeln(' ');
94 | $output->writeln('Setting the FULL_CACHE flag');
95 | $dwarfIterator = new \ArrayIterator($dwarves);
96 | $cachingDwarfIterator = new CustomCachingIterator($dwarfIterator, \CachingIterator::FULL_CACHE);
97 |
98 | // Load the cache;
99 | foreach ($cachingDwarfIterator as $thisDwarf) {
100 | };
101 |
102 | $cachingDwarfIterator->removeBashful();
103 |
104 | $output->writeln(' ');
105 | $output->writeln(' Cached');
106 |
107 | foreach ($cachingDwarfIterator->getCache() as $key => $thisDwarf) {
108 | $output->writeln($key . " : " . $thisDwarf);
109 | } // foreach($dwarfIterator as $thisDwarf)
110 |
111 | $output->writeln(' ');
112 | $output->writeln(' This is the original iterator');
113 | foreach ($cachingDwarfIterator as $key => $thisDwarf) {
114 | $output->writeln($key . " - " . $thisDwarf);
115 | } // foreach($dwarfIterator as $thisDwarf)
116 |
117 |
118 | $output->writeln(' ');
119 | $output->writeln(" Now that we've modified an element, \n let's modify an element");
120 |
121 | $dwarfIterator = new \ArrayIterator($dwarves);
122 | $cachingDwarfIterator = new \CachingIterator($dwarfIterator, \CachingIterator::FULL_CACHE);
123 | // Load the cache;
124 | foreach ($cachingDwarfIterator as $thisDwarf) {
125 | };
126 |
127 | $cachingDwarfIterator[5] = 'Surley';
128 |
129 | $output->writeln(' ');
130 | $output->writeln(' Now let\'s out the inner cache');
131 | foreach ($cachingDwarfIterator->getCache() as $key => $thisDwarf) {
132 | $output->writeln($key . " : " . $thisDwarf);
133 | } // foreach($dwarfIterator as $thisDwarf)
134 |
135 |
136 | $output->writeln("Done");
137 | return;
138 | }
139 |
140 | }
141 |
--------------------------------------------------------------------------------
/examples/data.html:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 | Fraggle Rock Characters - Naming Schemes
5 |
6 |
7 |
9 |
10 |
11 |
13 |
14 |
16 |
18 |
19 |
21 |
26 |
27 |
28 |
74 |
171 |
174 |
178 |
179 |
180 |
181 |
182 |
183 |
184 |
185 |
186 |
187 |
Fraggle Rock Characters
188 |
189 |
190 |
191 |
192 |
From Naming Schemes
193 |
194 |
195 |
196 |
197 |
198 |
201 |
202 |
203 |
204 |
205 |
206 |
207 | Contents
208 |
220 | |
221 |
222 |
223 |
[edit] Fraggles
227 |
228 | - Boober
229 |
230 | - Gobo
231 |
232 | - Mokey
233 |
234 | - Red
235 |
236 | - Wembley
237 |
238 |
239 |
[edit] Doozers
242 |
243 |
244 | - Architect
245 |
246 | - Crosscut
247 |
248 | - Crusty
249 |
250 | - Cotterpin (Architects apprentice)
251 |
252 | - Flange (Cotterpin's father)
253 |
254 | - Flex
255 |
256 | - Hammerhead
257 |
258 | - Modem (Wrench's mother)
259 |
260 | - Wrench
261 |
262 |
263 |
266 |
267 | - Emperor of the Universe
268 |
269 | - Empress of the Universe
270 |
271 | - Gunge
272 |
273 | - Junior
274 |
275 | - Marjory
276 |
277 | - Philo
278 |
279 |
280 |
[edit] Outer Space
283 |
284 |
285 | - Doc
286 |
287 | - Sprocket
288 |
289 |
290 |
[edit] External Links
293 |
294 |
299 |
300 |
309 |
310 |
311 |
312 |
313 |
314 |
317 |
318 |
319 |
320 |
321 |
322 |
323 |
324 |
325 |
326 |
327 |
328 |
329 |
330 |
331 |
332 |
333 |
Personal tools
334 |
339 |
340 |
341 |
342 |
343 |
344 |
345 |
346 |
Namespaces
347 |
355 |
356 |
357 |
358 |
359 |
360 |
370 |
371 |
372 |
373 |
374 |
375 |
376 |
388 |
389 |
390 |
391 |
392 |
400 |
401 |
402 |
403 |
404 |
405 |
406 |
407 |
415 |
416 |
417 |
418 |
419 |
420 |
421 |
422 |
423 |
424 |
426 |
427 |
428 |
429 |
430 |
Navigation
431 |
432 |
444 |
445 |
446 |
447 |
448 |
449 |
450 |
451 |
452 |
453 |
454 |
Toolbox
455 |
456 |
472 |
473 |
474 |
475 |
476 |
477 |
478 |
479 |
480 |
481 |
482 |
503 |
504 |
507 |
508 |
511 |
512 |
516 |
521 |
522 |
523 |
524 |
525 |
--------------------------------------------------------------------------------