Skip to content

Commit e848e8b

Browse files
committed
Add a new level parameter to the PreOrder and PostOrder visitors.
1 parent 5c924b9 commit e848e8b

File tree

4 files changed

+87
-10
lines changed

4 files changed

+87
-10
lines changed

spec/drupol/phptree/Visitor/PostOrderVisitorSpec.php

+38
Original file line numberDiff line numberDiff line change
@@ -4,8 +4,13 @@
44

55
namespace spec\drupol\phptree\Visitor;
66

7+
use drupol\phptree\Node\NaryNode;
78
use drupol\phptree\Node\Node;
9+
use drupol\phptree\Node\ValueNode;
10+
use drupol\phptree\Render\GraphViz;
11+
use drupol\phptree\Visitor\BreadthFirstVisitor;
812
use drupol\phptree\Visitor\PostOrderVisitor;
13+
use Fhaculty\Graph\Graph;
914
use PhpSpec\ObjectBehavior;
1015

1116
class PostOrderVisitorSpec extends ObjectBehavior
@@ -34,4 +39,37 @@ public function it_can_traverse_a_tree()
3439
->traverse($tree)
3540
->shouldYield(new \ArrayIterator($nodes));
3641
}
42+
43+
public function it_can_traverse_a_tree_with_a_specific_level()
44+
{
45+
$tree = new NaryNode(2);
46+
47+
$data = \range('A', 'G');
48+
49+
$nodes = [];
50+
foreach ($data as $key => $value) {
51+
$nodes[$value] = new ValueNode($value);
52+
}
53+
54+
$tree->add(...array_values($nodes));
55+
56+
$nodes['root'] = $tree;
57+
58+
$order = [
59+
7 => $nodes['root'],
60+
];
61+
62+
$this
63+
->traverse($tree, 0)
64+
->shouldYield(new \ArrayIterator($order));
65+
66+
$order = [
67+
3 => $nodes['A'],
68+
6 => $nodes['B'],
69+
];
70+
71+
$this
72+
->traverse($tree, 1)
73+
->shouldYield(new \ArrayIterator($order));
74+
}
3775
}

spec/drupol/phptree/Visitor/PreOrderVisitorSpec.php

+35
Original file line numberDiff line numberDiff line change
@@ -4,7 +4,9 @@
44

55
namespace spec\drupol\phptree\Visitor;
66

7+
use drupol\phptree\Node\NaryNode;
78
use drupol\phptree\Node\Node;
9+
use drupol\phptree\Node\ValueNode;
810
use drupol\phptree\Visitor\PreOrderVisitor;
911
use PhpSpec\ObjectBehavior;
1012

@@ -34,4 +36,37 @@ public function it_can_traverse_a_tree()
3436
->traverse($tree)
3537
->shouldYield(new \ArrayIterator($rootAndNodes));
3638
}
39+
40+
public function it_can_traverse_a_tree_with_a_specific_level()
41+
{
42+
$tree = new NaryNode(2);
43+
44+
$data = \range('A', 'G');
45+
46+
$nodes = [];
47+
foreach ($data as $key => $value) {
48+
$nodes[$value] = new ValueNode($value);
49+
}
50+
51+
$tree->add(...array_values($nodes));
52+
53+
$nodes['root'] = $tree;
54+
55+
$order = [
56+
0 => $nodes['root'],
57+
];
58+
59+
$this
60+
->traverse($tree, 0)
61+
->shouldYield(new \ArrayIterator($order));
62+
63+
$order = [
64+
1 => $nodes['A'],
65+
5 => $nodes['B'],
66+
];
67+
68+
$this
69+
->traverse($tree, 1)
70+
->shouldYield(new \ArrayIterator($order));
71+
}
3772
}

src/Visitor/PostOrderVisitor.php

+7-5
Original file line numberDiff line numberDiff line change
@@ -19,23 +19,25 @@ class PostOrderVisitor extends AbstractVisitor
1919
/**
2020
* {@inheritdoc}
2121
*/
22-
public function traverse(NodeInterface $node): \Traversable
22+
public function traverse(NodeInterface $node, int $level = null): \Traversable
2323
{
2424
$this->index = 0;
2525

26-
return $this->doTraverse($node);
26+
return $this->doTraverse($node, $level);
2727
}
2828

2929
/**
3030
* {@inheritdoc}
3131
*/
32-
private function doTraverse(NodeInterface $node): \Traversable
32+
private function doTraverse(NodeInterface $node, int $level = null): \Traversable
3333
{
3434
foreach ($node->children() as $child) {
35-
yield from $this->doTraverse($child);
35+
yield from $this->doTraverse($child, $level);
3636
$this->index++;
3737
}
3838

39-
yield $this->index => $node;
39+
if (null === $level || $level === $node->depth()) {
40+
yield $this->index => $node;
41+
}
4042
}
4143
}

src/Visitor/PreOrderVisitor.php

+7-5
Original file line numberDiff line numberDiff line change
@@ -19,23 +19,25 @@ class PreOrderVisitor extends AbstractVisitor
1919
/**
2020
* {@inheritdoc}
2121
*/
22-
public function traverse(NodeInterface $node): \Traversable
22+
public function traverse(NodeInterface $node, int $level = null): \Traversable
2323
{
2424
$this->index = 0;
2525

26-
return $this->doTraverse($node);
26+
return $this->doTraverse($node, $level);
2727
}
2828

2929
/**
3030
* {@inheritdoc}
3131
*/
32-
private function doTraverse(NodeInterface $node): \Traversable
32+
private function doTraverse(NodeInterface $node, int $level = null): \Traversable
3333
{
34-
yield $this->index => $node;
34+
if (null === $level || $level === $node->depth()) {
35+
yield $this->index => $node;
36+
}
3537

3638
foreach ($node->children() as $child) {
3739
$this->index++;
38-
yield from $this->doTraverse($child);
40+
yield from $this->doTraverse($child, $level);
3941
}
4042
}
4143
}

0 commit comments

Comments
 (0)