Unordered rooted trees #
An unordered rooted tree with vertices labelled in α is a RoseTree α modulo the permutation
of children at every vertex: the quotient UnorderedTree α := Quotient RoseTree.isSetoid. In the
Connes–Kreimer literature these are the rooted trees and the ordered ones the planar rooted
trees ([Foi]); [marcolli-chomsky-berwick-2025] §1.1.3 builds
syntactic objects on them, since Merge is set formation and {α, {β, γ}} has no order. The
identity criterion is RoseTree.Perm (Core/Data/RoseTree/Perm.lean); this file owns the
quotient: the projection mk, the lifting API, the lifted invariants, and the constructor node
on Multiset children, under which the grafting B⁺ of a multiset of trees is well defined.
Main definitions #
UnorderedTree,UnorderedTree.mk: the quotient and its projection; operations descend throughQuotient.liftand proofs throughQuotient.inductionOn, as forMultiset.UnorderedTree.cons: adjoin a tree as a further child of the root, the transport of the list cons on children; it is left-commutative, soMultiset.foldrbuilds the constructorUnorderedTree.nodeon a multiset of children computably.
References #
- [M. Marcolli, N. Chomsky and R. C. Berwick, Mathematical Structure of Syntactic Merge (2025)][marcolli-chomsky-berwick-2025]
- L. Foissy, An introduction to Hopf algebras of trees
The quotient type #
An unordered rooted tree with α-labelled vertices: the quotient of RoseTree α by the
permutation of children at every vertex, RoseTree.Perm.
Equations
- UnorderedTree α = Quotient RoseTree.isSetoid
Instances For
The canonical projection from ordered to nonplanar trees.
Equations
- UnorderedTree.mk t = ⟦t⟧
Instances For
Two trees give the same nonplanar tree iff they're RoseTree.Perm-related.
Smart leaf constructor + lifted counts #
A leaf in UnorderedTree α is mk (RoseTree.leaf a). numNodes is the
canonical first lifted invariant.
A nonplanar leaf labeled a.
Equations
Instances For
The node count (number of vertices) of a nonplanar tree, lifted
from RoseTree.numNodes via RoseTree.Perm-invariance.
Equations
- UnorderedTree.numNodes = Quotient.lift RoseTree.numNodes ⋯
Instances For
The leaf count (number of childless vertices) of a nonplanar tree,
lifted from RoseTree.numLeaves via RoseTree.Perm-invariance. MCB's
complexity grading #L (Def. 1.6.2) is built on this.
Equations
- UnorderedTree.numLeaves = Quotient.lift RoseTree.numLeaves ⋯
Instances For
The arity (root child count) of a nonplanar tree.
Equations
- UnorderedTree.arity = Quotient.lift RoseTree.arity ⋯
Instances For
The height (number of vertices on a longest root-to-leaf path) of a nonplanar tree.
Equations
- UnorderedTree.height = Quotient.lift RoseTree.height ⋯
Instances For
Destructors and node injectivity #
The root value and the children (as a multiset of nonplanar trees) are
RoseTree.Perm-invariant, so they descend to UnorderedTree. congrArg on these destructors
inverts mk-equality at a node with no induction, giving the injectivity
characterization mk_node_eq_mk_node_iff.
The root value of a nonplanar tree.
Equations
- UnorderedTree.value = Quotient.lift RoseTree.value ⋯
Instances For
The children of a nonplanar tree, as a multiset of nonplanar trees.
Equations
- UnorderedTree.children = Quotient.lift (fun (t : RoseTree α) => ↑(List.map UnorderedTree.mk t.children)) ⋯
Instances For
Injectivity of the node constructor on the quotient: mk-images of two nodes are
equal iff the root values agree and the children agree as multisets of nonplanar
trees. The forward direction is congrArg on the value and children
destructors; the backward direction assembles a RoseTree.Perm componentwise.
Adjoining a child, and the node constructor #
cons c t adjoins c as a further child of the root of t; it is the transport of the list
cons on children lists and is left-commutative, so node a F is its Multiset.foldr over the
children F starting from the leaf a. Both are computable, and node_mk_tree_list reads
node back on a list of planar children.
Adjoin a tree as a further child of the root.
Equations
- c.cons t = Quotient.liftOn₂ c t (fun (c t : RoseTree α) => UnorderedTree.mk (RoseTree.node t.value (c :: t.children))) ⋯
Instances For
Build an unordered tree from a label and a multiset of children, by adjoining the children one at a time to the leaf.
Equations
- UnorderedTree.node a F = Multiset.foldr UnorderedTree.cons (UnorderedTree.leaf a) F
Instances For
The empty-forest node is the leaf.
Binary case of node_mk_tree_list: a bare pair of mk-lifted trees.
Choose planar representatives for a whole forest at once: every
Multiset (UnorderedTree α) is the mk-image of a list of planar trees. Descent
proofs that use this eliminator meet node_mk_tree_list on the nose, with no
Quotient.out repair.
Eta law: every tree is the node of its root value and children.
Every tree has at least one vertex (the root).
Node count of a smart-constructor node: one (the root) plus the
total node count of the children multiset.
A tree's height is strictly less than the height of any node containing it as a child.
Functoriality #
Lift RoseTree.map through the quotient. Counterpart of List.map for
lists: a function f : α → β lifts to UnorderedTree α → UnorderedTree β by
relabeling every vertex.
Map a function over the vertex labels of a nonplanar rooted tree.
Lifted from RoseTree.map via Quotient.map.
Equations
- UnorderedTree.map f = Quotient.map (RoseTree.map f) ⋯
Instances For
Quotient-unfolding for UnorderedTree.map. Plain lemma (not @[simp])
since mathlib's generic Quotient.map_mk covers the same ground.