Composable states with unidirectional value propagation for enumerating combinatorial spaces
Project description
StateTracker
StateTracker is a Python library for creating composable states with unidirectional value propagation. It provides a powerful way to enumerate combinatorial spaces through state algebra operations.
Why StateTracker?
StateTracker was developed to support the design of complex DNA sequence libraries (see PoolParty), but it solves a general problem: random access to combinatorial spaces.
If you've ever written nested loops to enumerate a Cartesian product and then wished you could shuffle the order, sample a subset, or split into train/test sets—all while tracking which component indices correspond to each item—StateTracker is for you. Build your combinatorial structure once using state algebra, and StateTracker handles the index math automatically.
Features
- Composable States: Build complex iteration patterns from simple states
- Unidirectional Value Propagation: Set child value and parent values update automatically
- State Algebra: Product (×), sum (+), slice, repeat, shuffle, and synchronize operations
- Conflict Detection: Automatic detection of conflicting value assignments
- Tree Visualization: Built-in ASCII tree visualization for debugging
Installation
pip install statetracker
For development:
git clone https://github.com/jbkinney/poolparty-statetracker.git
cd poolparty-statetracker/statetracker
pip install -e ".[dev]"
Quick Start
from statetracker import State, Manager, product, stack, repeat, shuffle, sync
with Manager():
# Create leaf states
A = State(num_values=2, name='A')
B = State(num_values=3, name='B')
# Combine with product (Cartesian product)
C = product([A, B]) # 6 values total
# Iterate and see parent values update
for value in C:
print(f"C={value}, A={A.value}, B={B.value}")
Output:
C=0, A=0, B=0
C=1, A=1, B=0
C=2, A=0, B=1
C=3, A=1, B=1
C=4, A=0, B=2
C=5, A=1, B=2
State Operations
Product (Cartesian Product)
with Manager():
A = State(num_values=2, name='A')
B = State(num_values=3, name='B')
C = product([A, B]) # 6 values (2 × 3)
Stack
with Manager():
A = State(num_values=2, name='A')
B = State(num_values=3, name='B')
C = stack([A, B]) # 5 values (2 + 3)
for _ in C:
# Only one of A or B is active (non-None) at a time
print(f"A={A.value}, B={B.value}")
Slicing
with Manager():
A = State(num_values=10, name='A')
B = A[2:5] # Values 2, 3, 4
C = A[::2] # Even values: 0, 2, 4, 6, 8
D = A[::-1] # Reversed: 9, 8, 7, ..., 0
Repeat
with Manager():
A = State(num_values=3, name='A')
B = repeat(A, 4) # Repeat A four times (12 values)
Shuffle
with Manager():
A = State(num_values=5, name='A')
B = shuffle(A, seed=42) # Randomly permuted order
Synchronize
with Manager():
A = State(num_values=4, name='A')
B = State(num_values=4, name='B')
sync(A, B) # A and B always have same value
Value Propagation
StateTracker uses unidirectional value propagation. When you set a child state's value, all parent states automatically update:
with Manager():
A = State(num_values=2, name='A')
B = State(num_values=3, name='B')
C = product([A, B])
C.value = 5 # Set child value
print(A.value) # 1 (automatically updated)
print(B.value) # 2 (automatically updated)
Visualization
Visualize state dependencies with ASCII trees:
with Manager():
A = State(num_values=2, name='A')
B = State(num_values=3, name='B')
C = product([A, B])
C.name = 'C'
C.print_dag(style='minimal')
Output:
C (n=6)
└── [Product]
├── A (n=2)
└── B (n=3)
Documentation
Full documentation is available at statetracker.readthedocs.io.
License
MIT License - see LICENSE for details.
Project details
Release history Release notifications | RSS feed
Download files
Download the file for your platform. If you're not sure which to choose, learn more about installing packages.
Source Distribution
Built Distribution
Filter files by name, interpreter, ABI, and platform.
If you're not sure about the file name format, learn more about wheel file names.
Copy a direct link to the current filters
File details
Details for the file statetracker-0.1.1.tar.gz.
File metadata
- Download URL: statetracker-0.1.1.tar.gz
- Upload date:
- Size: 25.4 kB
- Tags: Source
- Uploaded using Trusted Publishing? No
- Uploaded via: uv/0.9.18 {"installer":{"name":"uv","version":"0.9.18","subcommand":["publish"]},"python":null,"implementation":{"name":null,"version":null},"distro":{"name":"macOS","version":null,"id":null,"libc":null},"system":{"name":null,"release":null},"cpu":null,"openssl_version":null,"setuptools_version":null,"rustc_version":null,"ci":null}
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
16f2fdec94e3fb8582a703e469787c6a4bd4bf6d3a3bb09faf6cf89c1ae109e7
|
|
| MD5 |
6000d85fb5927adc4fbc885ff0f18e4b
|
|
| BLAKE2b-256 |
655d948ac33090c8da8c13e0acbe4533f2f8d96adc8dc2e4dc0c863f33736abe
|
File details
Details for the file statetracker-0.1.1-py3-none-any.whl.
File metadata
- Download URL: statetracker-0.1.1-py3-none-any.whl
- Upload date:
- Size: 24.1 kB
- Tags: Python 3
- Uploaded using Trusted Publishing? No
- Uploaded via: uv/0.9.18 {"installer":{"name":"uv","version":"0.9.18","subcommand":["publish"]},"python":null,"implementation":{"name":null,"version":null},"distro":{"name":"macOS","version":null,"id":null,"libc":null},"system":{"name":null,"release":null},"cpu":null,"openssl_version":null,"setuptools_version":null,"rustc_version":null,"ci":null}
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
b55019f1476850a2841d886f302357c11adf60e5eeca9686b7ba5548d37190ac
|
|
| MD5 |
cdd769e85a07e6bdff3dbbacf4d7858c
|
|
| BLAKE2b-256 |
adc7dc7875e50ed81c87de6b28932fa2392e92e741b9a244634662a78215020c
|