Skip to content

Commit

Permalink
Added fold and filter methods
Browse files Browse the repository at this point in the history
  • Loading branch information
nozavroni committed Mar 18, 2018
1 parent 52deeea commit 9f6473b
Show file tree
Hide file tree
Showing 3 changed files with 94 additions and 0 deletions.
33 changes: 33 additions & 0 deletions src/Collection/Collection.php
Expand Up @@ -357,6 +357,39 @@ public function deduplicate()
return $this;
}

/**
* Return a new collection with only filtered keys/values
*
* The callback accepts value, key, index and should return true if the item should be added to the returned
* collection
*
* @param callable $callback
*
* @return Collection
*/
public function filter(callable $callback)
{
$collection = static::factory();
$index = 0;
foreach ($this as $key => $value) {
if ($callback($value, $key, $index++)) {
$collection->set($key, $value);
}
}

return $collection;
}

public function fold($callback, $initial = null)
{
$index = 0;
$folded = $initial;
foreach ($this as $key => $val) {
$folded = $callback($folded, $val, $key, $index++);
}
return $folded;
}

/** ++++ ++++ **/
/** ++ Interface Compliance ++ **/
/** ++++ ++++ **/
Expand Down
52 changes: 52 additions & 0 deletions tests/Tests/CollectionTest.php
Expand Up @@ -173,6 +173,58 @@ public function testDeduplicateRemovesDuplicatesInPlace()
], $col->toArray());
}

public function testFilterKeepsOnlyItemsPassingTest()
{
$arr = $this->getFixture('numwords');
$col = new Collection($arr);

$filtered = $col->filter(function($val, $key) {
return is_int($val);
});
$this->assertEquals([
'two' => 2,
'four' => 4,
'five' => 5
], $filtered->toArray());

$filtered = $col->filter(function($val, $key) {
return is_int($key);
});
$this->assertEquals([
0 => 'zero',
1 => 'one',
3 => 'three',
4 => 'four'
], $filtered->toArray());

$filtered = $col->filter(function($val, $key, $i) {
return $i % 2 == 0;
});
$this->assertEquals([
0 => 'zero',
'two' => 2,
'four' => 4,
4 => 'four'
], $filtered->toArray());
}

public function testFoldReturnsOneValue()
{
$arr = $this->getFixture('numwords');
$col = new Collection($arr);

$this->assertEquals(11, $col->fold(function($accum, $val, $key, $i) {
if (is_int($val)) {
return $accum + $val;
}
return $accum;
}));

$this->assertEquals('[[[[[[[init-zero-0-0]-one-1-1]-2-two-2]-three-3-3]-4-four-4]-5-five-5]-four-4-6]', $col->fold(function($accum, $val, $key, $i) {
return "[{$accum}-{$val}-{$key}-{$i}]";
}, 'init'), 'Initial value passed in should be the first value of $accum');
}

/**
* @expectedException RuntimeException
*/
Expand Down
9 changes: 9 additions & 0 deletions tests/Tests/TestCase.php
Expand Up @@ -30,6 +30,15 @@ public function setUp()
'secondthree' => 3,
'thirdzero' => 0
];
$this->fixtures['numwords'] = [
0 => 'zero',
1 => 'one',
'two' => 2,
3 => 'three',
'four' => 4,
'five' => 5,
4 => 'four'
];
}

public function tearDown()
Expand Down

0 comments on commit 9f6473b

Please sign in to comment.