Skip to main content

Multiple dispatch in JAX via custom interpreters.

Project description

Quax

JAX + multiple dispatch + custom array-ish objects

For example, this can be mean overloading matrix multiplication to exploit sparsity or structure, or automatically rewriting a LoRA's matmul (W + AB)v into the more-efficient Wv + ABv.

Applications include:

  • LoRA weight matrices
  • symbolic zeros
  • arrays with named dimensions
  • structured (e.g. tridiagonal) matrices
  • sparse arrays
  • quantised arrays
  • arrays with physical units attached
  • etc! (See the built-in quax.examples library for most of the above!)

This works via a custom JAX transform. Take an existing JAX program, wrap it in a quax.quaxify, and then pass in the custom array-ish objects. This means it will work even with existing programs, that were not written to accept such array-ish objects!

(Just like how jax.vmap takes a program, but reinterprets each operation as its batched version, so to will quax.quaxify take a program and reinterpret each operation according to what array-ish types are passed.)

Installation

pip install quax

Documentation

Available at https://nstarman.github.io/quax.

Example: LoRA

This example demonstrates everything you need to use the built-in quax.examples.lora library.

import equinox as eqx
import jax.random as jr
import quax
import quax.examples.lora as lora

#
# Start off with any JAX program: here, the forward pass through a linear layer.
#

key1, key2, key3 = jr.split(jr.PRNGKey(0), 3)
linear = eqx.nn.Linear(10, 12, key=key1)
vector = jr.normal(key2, (10,))

def run(model, x):
  return model(x)

run(linear, vector)  # can call this as normal

#
# Now let's Lora-ify it.
#

# Step 1: make the weight be a LoraArray.
lora_weight = lora.LoraArray(linear.weight, rank=2, key=key3)
lora_linear = eqx.tree_at(lambda l: l.weight, linear, lora_weight)
# Step 2: quaxify and call the original function. The transform will call the
# original function, whilst looking up any multiple dispatch rules registered.
# (In this case for doing matmuls against LoraArrays.)
quax.quaxify(run)(lora_linear, vector)
# Appendix: Quax includes a helper to automatically apply Step 1 to all
# `eqx.nn.Linear` layers in a model.
lora_linear = lora.loraify(linear, rank=2, key=key3)

Work in progress!

Right now, the following are not supported:

  • jax.custom_vjp

It should be fairly straightforward to add support for these; open an issue or pull request. (We've already got jax.custom_jvp, jax.lax.cond_p, jax.lax.while_p, and jax.lax.scan_p. :) )

See also: other libraries in the JAX ecosystem

Always useful
Equinox: neural networks and everything not already in core JAX!
jaxtyping: type annotations for shape/dtype of arrays.

Deep learning
Optax: first-order gradient (SGD, Adam, ...) optimisers.
Orbax: checkpointing (async/multi-host/multi-device).
Levanter: scalable+reliable training of foundation models (e.g. LLMs).

Scientific computing
Diffrax: numerical differential equation solvers.
Optimistix: root finding, minimisation, fixed points, and least squares.
Lineax: linear solvers.
BlackJAX: probabilistic+Bayesian sampling.
sympy2jax: SymPy<->JAX conversion; train symbolic expressions via gradient descent.
PySR: symbolic regression. (Non-JAX honourable mention!)

Built on Quax
Quaxed: a namespace of already-wrapped quaxify(jnp.foo) operations.
unxt: Unitful Quantities.

Awesome JAX
Awesome JAX: a longer list of other JAX projects.

Acknowledgements

Significantly inspired by https://github.com/davisyoshida/qax, https://github.com/stanford-crfm/levanter, and jax.experimental.sparse.

Project details


Download files

Download the file for your platform. If you're not sure which to choose, learn more about installing packages.

Source Distribution

quax-0.3.6.tar.gz (175.8 kB view details)

Uploaded Source

Built Distribution

If you're not sure about the file name format, learn more about wheel file names.

quax-0.3.6-py3-none-any.whl (40.9 kB view details)

Uploaded Python 3

File details

Details for the file quax-0.3.6.tar.gz.

File metadata

  • Download URL: quax-0.3.6.tar.gz
  • Upload date:
  • Size: 175.8 kB
  • Tags: Source
  • Uploaded using Trusted Publishing? Yes
  • Uploaded via: twine/6.1.0 CPython/3.13.13

File hashes

Hashes for quax-0.3.6.tar.gz
Algorithm Hash digest
SHA256 f879f9c9945393281cf219b76d4e531ef3b50e88b864041ab159c95305eef451
MD5 af623865a832ca5140db609cab685058
BLAKE2b-256 bb097d59f59e558f2fb573abef5a15d107f845d59f2b42cf9c40d7d92f7b13cf

See more details on using hashes here.

Provenance

The following attestation bundles were made for quax-0.3.6.tar.gz:

Publisher: cd.yml on nstarman/quax

Attestations: Values shown here reflect the state when the release was signed and may no longer be current.

File details

Details for the file quax-0.3.6-py3-none-any.whl.

File metadata

  • Download URL: quax-0.3.6-py3-none-any.whl
  • Upload date:
  • Size: 40.9 kB
  • Tags: Python 3
  • Uploaded using Trusted Publishing? Yes
  • Uploaded via: twine/6.1.0 CPython/3.13.13

File hashes

Hashes for quax-0.3.6-py3-none-any.whl
Algorithm Hash digest
SHA256 dbe08ddca8d6df4383feffa5943f7bceaa4d273fd588901d2a5819e36ffce815
MD5 4aa8c2032f3ba69034f9e2e624d25735
BLAKE2b-256 1d8dc3fd4c78ba0a128b79053a279bc5de4db6b81bcf8476726d45c64ff46b8b

See more details on using hashes here.

Provenance

The following attestation bundles were made for quax-0.3.6-py3-none-any.whl:

Publisher: cd.yml on nstarman/quax

Attestations: Values shown here reflect the state when the release was signed and may no longer be current.

Supported by

AWS Cloud computing and Security Sponsor Datadog Monitoring Depot Continuous Integration Fastly CDN Google Download Analytics Pingdom Monitoring Sentry Error logging StatusPage Status page