Skip to main content

Data-driven surrogates for hyperelastic constitutive models in finite element analysis

Project description

hyper-surrogate

Release Build status codecov License

Define hyperelastic materials in Python, deploy them in your finite element solver.

Table of Contents

Why hyper-surrogate?

Finite element solvers need constitutive models. Writing and maintaining those models — especially user-material subroutines for Abaqus, FEAP and similar Fortran-based solvers — is repetitive: kinematics, second Piola–Kirchhoff stress, consistent tangent, Jaumann correction, reference-configuration freedom, all in Fortran 77 or 90.

hyper-surrogate lets you define your material once in Python and emit a self-contained Fortran 90 user subroutine deployable in any Fortran-based FE solver. You choose how the material is defined:

  1. Built-in symbolic SEF — one of ten classical isotropic and anisotropic models (Neo-Hooke, Mooney-Rivlin, Yeoh, Holzapfel-Ogden, Gasser-Ogden-Holzapfel, …).
  2. Custom symbolic SEF — subclass Material with a sef property in SymPy and the framework derives stress and tangent automatically.
  3. Data-driven surrogate — train an MLP, ICNN, or polyconvex ICNN on energy and stress samples from any ground-truth source and emit a hybrid UMAT whose energy is the trained network and whose stress and tangent are computed analytically in Fortran.

All three paths produce the same artefact: a .f90 with Cauchy stress, analytical consistent tangent, and stress-freedom at the reference configuration enforced exactly at emission time. No Python runtime is required at solve time.

Architecture

Material ─> DeformationGenerator ─> Dataset ─> MLP / ICNN ─> HybridUMATEmitter ─> .f90
   │                                              │
   │         (symbolic SEF)                        │  (trained NN weights)
   │                                              │
   └──── UMATHandler ─────────────────────────────┘
         (analytical Fortran via SymPy CSE)

Features

  • Three entry points, one output — built-in SEF, custom SymPy SEF, or trained surrogate, all emit a structurally identical Fortran UMAT.
  • Symbolic mechanics — automatic PK2 stress and stiffness tensor derivation via SymPy; analytical Cauchy push-forward and Jaumann correction emitted with common-subexpression elimination.
  • NN architectures — MLP, Input-Convex NN, and polyconvex ICNN, trained with an energy-plus-stress dual loss that backpropagates the gradient target through autograd.
  • Hybrid UMAT — neural-network strain energy with closed-form analytical kinematics, stress, and consistent tangent in Fortran; layer-additive Hessian backpropagation verified against autograd at $10^{-5}$ tolerance.
  • Stress freedom at reference — enforced exactly at emission time by subtracting a compile-time offset; no surprise residual stress at $\mathbf{C} = \mathbf{I}$.
  • Anisotropic support — fiber pseudo-invariants $I_4, I_5$ for one or two fiber families with arbitrary orientations.

Quick Start

Three short pipelines, mirroring the three ways to define a material:

Path A — built-in symbolic SEF

from hyper_surrogate import NeoHooke, UMATHandler

UMATHandler(NeoHooke({"C10": 0.5, "KBULK": 1000.0})).generate("neohooke.f90")

Path B — custom user-defined SEF

import sympy as sp
from hyper_surrogate import Material, UMATHandler

class MyOgdenLike(Material):
    DEFAULT_PARAMS = {"mu": 1.0, "alpha": 2.0, "KBULK": 1000.0}

    def __init__(self, parameters=None):
        super().__init__({**self.DEFAULT_PARAMS, **(parameters or {})})

    @property
    def sef(self):
        h = self._handler
        mu, alpha, K = (self._symbols[k] for k in ("mu", "alpha", "KBULK"))
        return ((mu / alpha) * (h.isochoric_invariant1 ** (alpha / 2) - 3)
                + 0.5 * K * (sp.sqrt(h.invariant3) - 1) ** 2)

UMATHandler(MyOgdenLike()).generate("mysef.f90")

Path C — data-driven surrogate

from hyper_surrogate import (
    NeoHooke, MLP, Trainer, EnergyStressLoss,
    create_datasets, extract_weights, HybridUMATEmitter,
)

material = NeoHooke({"C10": 0.5, "KBULK": 1000.0})
train_ds, val_ds, in_norm, energy_norm = create_datasets(
    material, n_samples=4000, input_type="invariants",
    target_type="energy", deformation_mode="combined_compressible",
)
model = MLP(input_dim=3, output_dim=1, hidden_dims=[64, 64, 64], activation="softplus")
result = Trainer(model, train_ds, val_ds,
                 loss_fn=EnergyStressLoss(alpha=1.0, beta=1.0),
                 max_epochs=2000, patience=200).fit()
exported = extract_weights(result.model, in_norm, energy_norm)
HybridUMATEmitter(exported).write("neohooke_hybrid.f90")

See the documentation for the full tutorial set, including custom materials, anisotropic models, and the export-path decision tree.

Installation

pip install hyper-surrogate        # core (NumPy, SymPy)
pip install hyper-surrogate[ml]    # with PyTorch for ML surrogates

From source with uv:

git clone https://github.com/jpsferreira/hyper-surrogate.git
cd hyper-surrogate
uv sync --all-groups --extra ml

Examples

Runnable scripts are in the examples/ directory:

Script Path Description
analytical_umat.py A Built-in NeoHooke → analytical UMAT via UMATHandler
custom_sef.py B Custom Ogden-like SEF → analytical UMAT
export_hybrid_umat.py C End-to-end train + HybridUMATEmitter export
train_neohooke_sef.py C Train MLP on NeoHooke SEF with hybrid inference
train_icnn_energy.py C Train ICNN with EnergyStressLoss
train_polyconvex.py C Train PolyconvexICNN with per-invariant convexity
train_holzapfel_ogden.py C Anisotropic fiber-reinforced training pipeline

Run any example with:

uv run python examples/<script>.py

Contributing

Contributions are welcome! See CONTRIBUTING.md for setup instructions and guidelines.

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

hyper_surrogate-0.4.0.tar.gz (310.1 kB view details)

Uploaded Source

Built Distribution

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

hyper_surrogate-0.4.0-py3-none-any.whl (62.2 kB view details)

Uploaded Python 3

File details

Details for the file hyper_surrogate-0.4.0.tar.gz.

File metadata

  • Download URL: hyper_surrogate-0.4.0.tar.gz
  • Upload date:
  • Size: 310.1 kB
  • Tags: Source
  • Uploaded using Trusted Publishing? No
  • Uploaded via: uv/0.11.15 {"installer":{"name":"uv","version":"0.11.15","subcommand":["publish"]},"python":null,"implementation":{"name":null,"version":null},"distro":{"name":"Ubuntu","version":"24.04","id":"noble","libc":null},"system":{"name":null,"release":null},"cpu":null,"openssl_version":null,"setuptools_version":null,"rustc_version":null,"ci":true}

File hashes

Hashes for hyper_surrogate-0.4.0.tar.gz
Algorithm Hash digest
SHA256 df7ee90e17b7c841b791c728df76e6e3dfdca8e211a1e5c5248ba3fed3f92cfd
MD5 357a133baade590cbabea10e545c4486
BLAKE2b-256 5300bc450bb455ee37c941b9b34bed03e444b538296b162edb1c3f6e47bc4fbf

See more details on using hashes here.

File details

Details for the file hyper_surrogate-0.4.0-py3-none-any.whl.

File metadata

  • Download URL: hyper_surrogate-0.4.0-py3-none-any.whl
  • Upload date:
  • Size: 62.2 kB
  • Tags: Python 3
  • Uploaded using Trusted Publishing? No
  • Uploaded via: uv/0.11.15 {"installer":{"name":"uv","version":"0.11.15","subcommand":["publish"]},"python":null,"implementation":{"name":null,"version":null},"distro":{"name":"Ubuntu","version":"24.04","id":"noble","libc":null},"system":{"name":null,"release":null},"cpu":null,"openssl_version":null,"setuptools_version":null,"rustc_version":null,"ci":true}

File hashes

Hashes for hyper_surrogate-0.4.0-py3-none-any.whl
Algorithm Hash digest
SHA256 33637e243bc081ee900ac1bd7e0aa4702262df397f88b8c5567a18255301da45
MD5 2f65d2cc33cb96a504eba3c923208378
BLAKE2b-256 8a1888f06d4bde57ae492e7d07f973e3e22758d1483f3c9c692d1da3f00b3bfa

See more details on using hashes here.

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