|claim|login
RepoCritics — Review. Share. Archive. Every open-source repo.

TuringLang/Turing.jl

Wiki: TuringLang/Turing.jl

Source: https://github.com/TuringLang/Turing.jl

Last synced 2026-07-18 · 1136 words · Edit wiki on GitHub →

TuringLang/Turing.jl

> General-purpose probabilistic programming in Julia — Bayesian models as ordinary Julia functions, sampled with MCMC or fit variationally.

GitHub repo · Official website · License: MIT

Overview

Turing.jl is a probabilistic programming language (PPL) embedded in Julia, started at the University of Cambridge by Hong Ge in 2016 and formally described at AISTATS 20181. A model is a Julia function annotated with the @model macro; ~ statements declare random variables, and any Julia code — loops, conditionals, calls into ODE solvers or neural network layers — can appear in the model body. This "dynamic" design is the core bet: where Stan restricts you to a fixed-shape model in a dedicated language compiled to C++, Turing lets the model be arbitrary Julia, including models whose dimensionality changes stochastically at runtime2.

The tradeoff is that flexibility pushes work onto the user and the compiler: performance depends heavily on how the model is written, gradient-based samplers depend on Julia's still-uneven automatic differentiation ecosystem, and first-run latency inherits Julia's compile-time costs. Turing itself is a facade — the front door to a dozen smaller, independently versioned TuringLang packages3. It is maintained primarily by academic researchers at grant-funded institutions with explicitly limited triage capacity4, yet is genuinely active (pushed within days as of mid-2026, ~2.2k stars, fortnightly ecosystem newsletter, 2025 journal paper in ACM TOPML5).

Getting Started

Requires Julia (≥ 1.10.8 for current releases)4:

julia> using Pkg; Pkg.add("Turing")
using Turing

@model function linear_regression(x)
    # Priors
    α ~ Normal(0, 1)
    β ~ Normal(0, 1)
    σ² ~ truncated(Cauchy(0, 3); lower=0)

    # Likelihood
    μ = α .+ β .* x
    y ~ MvNormal(μ, σ² * I)
end

x, y = rand(10), rand(10)
posterior = linear_regression(x) | (; y = y)   # condition on observed y
chain = sample(posterior, NUTS(), 1000)

The | conditioning syntax means one model definition serves both generative simulation and inference.

Architecture / How It Works

Turing.jl itself is mostly glue. The real machinery lives in sibling packages under the TuringLang organization3:

  • DynamicPPL.jl — the model DSL. @model rewrites each ~ statement into

a call that either assumes (samples a latent variable) or observes (accumulates log-likelihood), depending on what the model has been conditioned on; values and metadata live in a VarInfo structure threaded through model execution.

  • AbstractMCMC.jl — the minimal sampler interface all samplers implement,

including chain parallelism via MCMCThreads() / MCMCDistributed().

  • AdvancedHMC.jl — HMC/NUTS; AdvancedMH.jl — Metropolis–Hastings;

AdvancedPS.jl — particle methods (SMC, particle Gibbs), which are what make stochastic control flow and varying dimension tractable.

  • Bijectors.jl — maps constrained parameters (e.g. a positive σ²) to

unconstrained space so HMC can operate freely; AdvancedVI.jl — variational inference; Optimization.jl (SciML) backs MLE/MAP; MCMCChains.jl — the Chains result type with R-hat/ESS diagnostics.

Gradient-based samplers need AD over the model's log density; the preferred backends are ForwardDiff.jl and Mooncake.jl, with others available through DifferentiationInterface.jl4. Samplers compose: Gibbs can assign NUTS to continuous parameter blocks and particle Gibbs to discrete ones — something Stan cannot do at all without manual marginalization of discrete parameters.

Production Notes

Model style dominates performance. A naive port of a BUGS/Stan model — scalar observation loops, untyped containers, non-const globals — can be an order of magnitude slower than an idiomatic one using vectorized multivariate likelihoods and type-stable code. Profile the log density before blaming the sampler.

Choose the AD backend deliberately. ForwardDiff (the default) scales with parameter count; reverse-mode backends are the usual fix beyond roughly a hundred parameters. Historically Zygote was fragile around mutation inside models; Mooncake is the current preferred reverse-mode backend4. Backend switches can change both speed and whether a model differentiates at all.

Compile latency. The first sample call pays Julia's compilation cost — often tens of seconds for a nontrivial model. Julia 1.9+ native caching helped package loads, but per-model compilation remains, which makes Turing awkward for short-lived scripts and CLI-style batch jobs.

Interface churn. Turing has lived on 0.x versioning for most of its life, with breaking minor releases; sampler options, VarInfo internals, and AD selection have all shifted. Pin versions and read HISTORY.md first6.

Fragmented issue surface, limited capacity. Bugs frequently belong to DynamicPPL, AdvancedHMC, Bijectors, or an AD package rather than Turing.jl — stack traces span four or five packages. Maintainers migrate misfiled issues, but ask that new features be proposed before implementation; plan for slower review turnaround than commercially backed projects4.

When to Use / When Not

Use when:

  • Your model composes with the Julia ecosystem — ODEs (SciML), neural network

components, custom likelihoods written as plain Julia functions.

  • You need discrete parameters or stochastic control flow sampled directly

rather than marginalized by hand.

  • You are already in Julia and want priors-to-diagnostics in one language, with

generative and inference use from a single model definition.

Avoid when:

  • You need a battle-hardened, heavily diagnosed HMC stack with maximal

per-iteration speed on a static model — Stan remains the reference.

  • Your team is Python-based; PyMC or NumPyro deliver comparable capability

without a language switch.

  • Startup latency matters (short scripts, serverless, frequent cold restarts).
  • You need long-term interface stability an 0.x academic project cannot promise.

Alternatives

  • stan-dev/stan — use instead for the most mature, best-diagnosed HMC/NUTS

stack when your model fits Stan's static language.

  • pymc-devs/pymc — use instead when your team lives in Python and wants the

largest Bayesian modeling community.

  • pyro-ppl/numpyro — use instead for JAX-speed, GPU-friendly NUTS with a more

restricted functional modeling style.

  • pyro-ppl/pyro — use instead for deep probabilistic models and SVI at scale

on PyTorch.

  • blackjax-devs/blackjax — use instead for raw JAX sampler kernels when you

will write the log density yourself.

History

VersionDateNotes
2016-04Repository created; project started at Cambridge (Hong Ge)7.
2018-04AISTATS 2018 paper, "Turing: A Language for Flexible Probabilistic Inference"1.
2020Model DSL and compiler internals factored out into DynamicPPL.jl2.
2025-02Journal paper accepted at ACM Transactions on Probabilistic Machine Learning5.
2026-07Actively maintained; ~2.2k stars, MIT license, main + breaking branch release flow7.

References

  1. ^ Hong Ge, Kai Xu, Zoubin Ghahramani, "Turing: A Language for Flexible Probabilistic Inference" — AISTATS 2018, PMLR 84:1682-1690. https://proceedings.mlr.press/v84/ge18b.html
  2. ^ DynamicPPL.jl — the probabilistic-program DSL underlying Turing.jl. https://github.com/TuringLang/DynamicPPL.jl
  3. ^ TuringLang documentation, "Where does Turing.jl sit in the TuringLang ecosystem?". https://turinglang.org
  4. ^ Turing.jl README (maintenance capacity, AD backend policy, Julia version requirement). https://github.com/TuringLang/Turing.jl#readme
  5. ^ Fjelde et al., "Turing.jl: a general-purpose probabilistic programming language" — ACM Trans. Probab. Mach. Learn., 2025. https://doi.org/10.1145/3711897
  6. ^ Turing.jl changelog. https://github.com/TuringLang/Turing.jl/blob/main/HISTORY.md
  7. ^ GitHub repository metadata (created 2016-04-29; pushed 2026-07-17). https://github.com/TuringLang/Turing.jl

Tags

julia, bayesian-inference, probabilistic-programming, mcmc, hamiltonian-monte-carlo, variational-inference, statistics, machine-learning, scientific-computing