Generalize normalize function

dev
Bram van den Heuvel 2026-07-10 00:03:13 +02:00
parent eeac39a4fa
commit cbf8e29a84
1 changed files with 48 additions and 28 deletions

View File

@ -29,8 +29,24 @@ def normalize(term : Term) -> Term:
Create a normalization function. This function simplifies functions as
much as possible.
"""
def norm_iter(term : Term) -> Term:
"""
Normalize a single term. Use both the standard normalization scheme
"""
for func in _known_norms:
term = func(term)
return term
return traverse(f=norm_iter, term=term)
def register_known_const(name : str, value : Term) -> None:
_known_consts[name] = value
def register_known_norm(func : Callable[[Term], Term]) -> None:
_known_norms.append(func)
def std_norm_iter(term : Term) -> Term:
"""
Normalize a single term. Trust that all children values have
already been normalized, or that they will be normalized later on.
@ -44,7 +60,7 @@ def normalize(term : Term) -> Term:
case App():
match term.f:
case Lambda():
return term.f.substitute(value=norm_iter(term.x))
return term.f.substitute(value=term.x)
case _:
return term
@ -60,17 +76,16 @@ def normalize(term : Term) -> Term:
case Term():
return term
return traverse(f=norm_iter, term=term)
def register_known_const(name : str, value : Term) -> None:
_known_consts[name] = value
_known_norms.append(std_norm_iter)
def traverse(f : Callable[[Term], Term], term : Term) -> Term:
"""
Traverse through the tree back-and-forth, aiming to run the given
function as thoroughly as possible to manipulate the term tree.
The function quits once no more operations are created.
**WARNING:** This means the tree might traverse forever.
:param f: The traversal function that replaces terms.
:type f: Callable[[Term], Term]
:param term: The term to traverse.
@ -78,7 +93,12 @@ def traverse(f : Callable[[Term], Term], term : Term) -> Term:
:return: The result of the traversed term.
:rtype: Term
"""
return traverse_bottom_up(f=f, term=traverse_top_down(f=f, term=term))
a, b = Term(), term
while a != b:
a, b = b, traverse_bottom_up(f=f, term=traverse_top_down(f=f, term=term))
return b
def traverse_bottom_up(f : Callable[[Term], Term], term : Term) -> Term:
"""