After skimming through Fabien’s very interesting slideshare presentation on PHP 5.3 (no, I can’t read French), and playing with Jon Wage’s PHP Interactive Terminal, I whipped up a fun little object-oriented array-wrapper class to do some neat ruby-esque things. It should be noted this code is for fun, and probably not sufficient for production use.
Using my array class, the following functions are now possible:
// Instantiate the object
$test = new A(1, 2, 3, 4, 5, 6, 8, 10, 20);
// return an array containing the multiples of 4
$test->reduce(function($i) { return $i%4==0; });
// Sum up all even values
$x = 0;
$test->each(function($i) use (&$x) {
if($i % 2 != 0)
continue;
$x+=$i;
});
echo $i; // outputs "42";
// return the index of the first item evaluated true
$isGreaterThan = function($x, $y) { return $x > $y; };
$test->match(function($i) use ($isGreaterThan) { return $isGreaterThan($i, 15); });
// returns an array of all values multiplied by two
$test->map(function($i) { return $i*2; });
// until the function evaluates true, execute the block on all variables
$test->until(function($i) { return $i > 15; })->do(function($i) {
echo "This number ($i) is less than or equal to 15";
});
Although we really gain nothing here we don’t already have with functions such as array_walk, array_map, array_filter, and so on, I personally get slightly aroused at this ruby-esque PHP implementation. While not quite as pretty as ruby blocks, anonymous functions (aka “closures”) offer similar functionality. To make it more rubyesque, I’ve overloaded my class’s __call, and __invoke methods:
// Instantiate an existing array
$test = new A($fortunes);
// return an array with "in bed" appended to all fortunes
$test->map(function($i, $key) { return $i." in bed."; });
// mutate the array object in place (similar to ruby's exclamation mark convention)
$test->_map(function($i, $key) { return $i." in bed."; });
// the underscore convention works for all functions that return an array
$test->_reduce(function($i, $key) { return strpos($i, 'happiness') !== false; });
// Ruby-like array access
$test = new A(10, 900, 5, 30);
echo $test(1, 2) // returns array [900, 5] (starts at index 1, length is 2)
// maybe supported someday, if I have time:
echo $test['0..2'] // returns array [10, 900, 5] (starts at index 0, up to index 2)
echo $test['1..,-1'] // returns array [10, 900, 5] (starts at index 0, up to last index, excludes ending index)
$test['2...3'] = new A(2, 2); //inserts array as the given indexes, to produce array [10, 900, 2, 2, 2, 20]
You can check out my half-baked class here. Any other fun ideas??
*** Update ***
Jwage did something similar by wrapping primitive types in php classes. Check out his code here!


RSS Feed