Kauri is a Python package for symbolic and algebraic manipulation of rooted trees, with applications to B-series, Runge-Kutta methods, and backward error analysis. It implements multiple Hopf algebraic structures on both non-planar and planar rooted trees, and provides tools for symbolic computation, visualization, and numerical integration.
pip install kauri
The base install is lightweight (pure Python, no external dependencies) and provides tree algebra, enumeration, indexing, and Hopf algebraic operations.
For visualization, Runge-Kutta analysis, and B-series (requires matplotlib, numpy, scipy, sympy, tqdm):
pip install kauri[full]
Full documentation is available at https://kauri.readthedocs.io
| Algebra | Non-planar | Planar |
|---|---|---|
| Butcher-Connes-Kreimer (BCK) | kauri.bck |
kauri.nck |
| Grossman-Larson (GL) | kauri.gl |
kauri.pgl |
| Calaque-Ebrahimi-Fard-Manchon (CEM) | kauri.cem |
-- |
| Munthe-Kaas-Wright (MKW) | -- | kauri.mkw |
Each algebra provides: coproduct, counit, antipode, map_product, map_power.
Additionally, kauri.gl and kauri.pgl provide product, and kauri.mkw provides shuffle_product.
| Non-planar (commutative) | Planar (noncommutative) |
|---|---|
Tree |
PlanarTree |
Forest |
OrderedForest |
ForestSum |
ForestSum |
TensorProductSum |
TensorProductSum |
- B-series (
BSeries) -- symbolic and numerical manipulation of truncated B-series - Runge-Kutta methods (
RK) -- 15+ predefined methods with order verification, composition, and numerical integration - Commutator-free methods (
CFMethod) -- Lie group integrators with planar order theory - Odd-even decomposition (
oddeven,planar_oddeven) -- symmetric splitting of characters - Map algebra (
Map) -- BCK/CEM convolution products, composition, exp/log - Tree generation -- enumeration of non-planar, planar, and coloured trees
- SVG display -- inline visualization in Jupyter notebooks
import kauri as kr
import kauri.bck as bck
t = kr.Tree([[], [[]]])
cp = bck.coproduct(t)
kr.display(cp)t = kr.Tree([[[3],2],[1],0])
s = bck.antipode(t)
kr.display(s)import kauri.gl as gl
t = kr.Tree([[], [[]]])
cp = gl.coproduct(t)
kr.display(cp)import kauri.cem as cem
t = kr.Tree([[], [[]]])
cp = cem.coproduct(t)
kr.display(cp)import kauri.nck as nck
pt = kr.PlanarTree([[], [[]]])
cp = nck.coproduct(pt)
kr.display(cp)import kauri.pgl as pgl
t1 = kr.PlanarTree([[]])
t2 = kr.PlanarTree([[], []])
p = pgl.product(t1, t2)
kr.display(p)import kauri.mkw as mkw
pt = kr.PlanarTree([[], [[]]])
cp = mkw.coproduct(pt)
kr.display(cp)for t in kr.trees_of_order(4):
kr.display(t)t = kr.Tree([[],[]])
print(kr.rk_order_cond(t, s=3, explicit=True))a10**2*b1 + b2*(a20 + a21)**2 - 1/3
import sympy as sp
y1 = sp.symbols('y1')
y = sp.Matrix([y1])
f = sp.Matrix([y1 ** 2])
m = kr.rk4.elementary_weights_map()
bs = kr.BSeries(y, f, weights=m, order=5)
print(bs.series())import kauri.oddeven as oddeven
# The square root of the identity in BCK convolution
sqrt_id = oddeven.id_sqrt
# Verify: sqrt_id * sqrt_id == identity
t = kr.Tree([[],[]])
print((sqrt_id * sqrt_id)(t)) # Same as kr.ident(t)# Modified equation of a B-series method
phi = kr.rk4.elementary_weights_map()
mod_eq = phi.modified_equation()
# Preprocessed integrator
preprocessed = phi.preprocessed_integrator()If you found this library useful in your research, please consider citing:
@misc{shmelev2025ees,
title={Explicit and Effectively Symmetric Runge-Kutta Methods},
author={Shmelev, Daniil and Ebrahimi-Fard, Kurusch and Tapia, Nikolas and Salvi, Cristopher},
journal={arXiv:2507.21006},
year={2025}
}