the value of composite is that you trade some complexity for being able to not break encapsulation.
In your array version you are breaking encapsulation since you are testing if the node is not a leaf:
if(isset($node['children'])) $this->print($node['children']);
with composite you can say:
print();
then run-time polymorphism will call the right method. In this case (I'm not a PHP programmer so let me to use a Java-like syntax):
class Node {
void print() {
for (child in children) {
child.print();
}
}
...
}
class Leaf {
void print() {
// print it!
}
}
another advantage over plain array is that you are hiding your implementation details (data structure, etc)