# How to use a convolution integral with NeuralPDE.discretize

**URL:** https://discourse.julialang.org/t/how-to-use-a-convolution-integral-with-neuralpde-discretize/137997
**Category:** Modelling & Simulations
**Created:** [July 7, 2026, 10:53pm UTC](https://discourse.julialang.org/t/how-to-use-a-convolution-integral-with-neuralpde-discretize/137997 "2026-07-07T22:53:27Z")
**Posts on this page:** 9
**Page:** 1

<div class="post-metadata">

### Author: ![baez-rafael](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/baez-rafael/32/222377_2.png) [@baez-rafael](https://discourse.julialang.org/u/baez-rafael)
#### Post date: [July 7, 2026, 10:53pm UTC](https://discourse.julialang.org/t/how-to-use-a-convolution-integral-with-neuralpde-discretize/137997/1 "2026-07-07T22:53:27Z")

</div>

Hello everyone!

I am trying to include the convolution integral

\int\_0^tKr(t -\tau)\dot x(\tau)d\tau

in my equation and I keep coming up with this error when trying to do NeuralPDE.discretize

```julia
ERROR: KeyError: key :tau not found

```

Below is a reduced version of my code.

```julia
using NeuralPDE, ModelingToolkit, Optimization, OptimizationOptimJL
using DomainSets
using Lux: Chain, Dense

K_func(t) = exp(-t)*cos(t)

@parameters t 
@parameters tau
@variables x(..)

Dt = Differential(t)
DDt = Differential(t)^2

integral_tau = Integral(tau in DomainSets.ClosedInterval(0.0, t))

eq = DDt(x(t)) + integral_tau(K_func(t - tau) * Dt(x(tau))) + x(t) ~ 0

domains = [
    t ∈ Interval(0.0, 60.0),
    tau ∈ Interval(0.0, 60.0)
]

bcs = [
    x(0.0) ~ 0.0,
    Dt(x(0.0)) ~ 0.0,
]

chain = Chain([Dense(1, 4), Dense(4, 1)])
strategy = QuasiRandomTraining(10)
discretization = PhysicsInformedNN(chain, strategy)
@named pde_system = PDESystem(eq, bcs, domains, [t], [x])

prob = NeuralPDE.discretize(pde_system, discretization) # KeyError: key :tau not found

opt = Optim.LBFGS()
maxiters=1
res = Optimization.solve(prob, opt; maxiters)

```

This happens with julia v1.10.11 and the latest version right now, v1.12.6.  
This is on NeuralPDE v6.0.0

I’ve tried both @parameters and @variables; I understand that @parameters for independent variables and @variables are for functions of variables. I’m not sure where tau would fall under the current implementation.

I got a version running when I include tau as one of the independent variables, but that required also rewriting every instance of x(t) to also include tau “x(t, tau)”.

There was a somewhat similar issue a few years ago (I couldn’t find how to do the linked topic sorry, change the underscore to a dot, https://discourse.julialang\_org/t/way-to-write-the-integral-with-modelingtoolkit/82347/5), so I am hoping that this is an error on my part.

Any help would be greatly appreciated, thanks in advance!

---

<div class="post-metadata">

### Author: ![cmichelenstrofer](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/cmichelenstrofer/32/44392_2.png) [@cmichelenstrofer](https://discourse.julialang.org/u/cmichelenstrofer)
#### Post date: [July 8, 2026, 3:53pm UTC](https://discourse.julialang.org/t/how-to-use-a-convolution-integral-with-neuralpde-discretize/137997/3 "2026-07-08T15:53:07Z")

</div>

[Similar issue](https://discourse.julialang.org/t/way-to-write-the-integral-with-modelingtoolkit/82347/5) from a few years ago, but doesn’t seem to have a resolution either.

> [@Way to write the integral with ModelingToolkit](https://discourse.julialang.org/t/way-to-write-the-integral-with-modelingtoolkit/82347/5):
>
> Hi @ChrisRackauckas I tried what you suggested but I am unable to discretize the equation, below is the code and the error. I am not sure where to pass the parameter x. using NeuralPDE, Flux, ModelingToolkit, DiffEqFlux, DomainSets import ModelingToolkit: Interval @parameters t, x @variables u(..) lambda = -1.5 Di = Differential(t) Ii = Integral(x in DomainSets.ClosedInterval(0, t)) eq = Di(u(t)) + Ii((t-x)^lambda\*u(x)) ~ 1.0 bcs = [u(0.0) ~ 0.0] domains = [t ∈ Interval(0.0,2.0)] chain = Chain…

---

<div class="post-metadata">

### Author: ![mark.garnett](https://avatars.discourse-cdn.com/v4/letter/m/b9bd4f/32.png) [@mark.garnett](https://discourse.julialang.org/u/mark.garnett)
#### Post date: [July 10, 2026, 3:26pm UTC](https://discourse.julialang.org/t/how-to-use-a-convolution-integral-with-neuralpde-discretize/137997/4 "2026-07-10T15:26:29Z")

</div>

How WOULD your typical ODE solver be able to handle this type of integral, if the integral couldn’t some how be re-written as a system of ODEs? Because the step the integrator will take is not just dependent on the current state, but also the history of the state — the x(tau) term where tau ranges from time 0 to current time t.

But any ODE interface, you write a function that takes the current state x and returns the rates of change x\_dot. You don’t really have access to the state history, and although I suppose you could hack it in via some global variables  
your ODE integrator expects, AFAIK, for those rates to be dependent ONLY on the current state.

---

<div class="post-metadata">

### Author: ![baez-rafael](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/baez-rafael/32/222377_2.png) [@baez-rafael](https://discourse.julialang.org/u/baez-rafael)
#### Post date: [July 10, 2026, 5:31pm UTC](https://discourse.julialang.org/t/how-to-use-a-convolution-integral-with-neuralpde-discretize/137997/5 "2026-07-10T17:31:43Z")

</div>

@mark.garnett I understand the issue you’re pointing out. Looking more into this landed me onto a [MATLAB thread](https://www.mathworks.com/matlabcentral/answers/466124-convolution-integral-with-ode45) that describes a similar equation.

In the end they solved it in the ways you described. [One of the latest comment chains](https://www.mathworks.com/matlabcentral/answers/466124-convolution-integral-with-ode45#answer_1572702) describes how to rewrite as a coupled ODE under certain conditions. [Another comment chain](https://www.mathworks.com/matlabcentral/answers/466124-convolution-integral-with-ode45#comment_3346928) includes a few more solutions; namely a Laplace transform or storing the history.

In cases where the ODE can’t be rewritten; is it up to the user to store the history (using global variables or otherwise) like the MATLAB problem or is there an implementation I am missing? This also brings a different issue to mind, how does/could NeuralPDE handle this? To my understanding it doesn’t take steps in the same way a typical ODE solver does while training the Lux model.

---

<div class="post-metadata">

### Author: ![mark.garnett](https://avatars.discourse-cdn.com/v4/letter/m/b9bd4f/32.png) [@mark.garnett](https://discourse.julialang.org/u/mark.garnett)
#### Post date: [July 10, 2026, 5:44pm UTC](https://discourse.julialang.org/t/how-to-use-a-convolution-integral-with-neuralpde-discretize/137997/6 "2026-07-10T17:44:49Z")

</div>

I don’t know what to do if you can’t re-write the integral-differential equation as an ODE in the context of Modeling Toolkit. You don’t have access to the history of the variables AFAICT, maybe some of MTK devs have an idea of how.

I ran into this situation where the problem was heat diffusion into a semi-infinite space, where the surface temperature was a function of time, and because there was a 1/sqrt(t-tau) term in the integral that was beyond my mathematical powers to handle turn into a system of ODEs.

---

<div class="post-metadata">

### Author: ![cmichelenstrofer](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/cmichelenstrofer/32/44392_2.png) [@cmichelenstrofer](https://discourse.julialang.org/u/cmichelenstrofer)
#### Post date: [July 10, 2026, 6:15pm UTC](https://discourse.julialang.org/t/how-to-use-a-convolution-integral-with-neuralpde-discretize/137997/7 "2026-07-10T18:15:19Z")

</div>

> [@mark.garnett](#):
>
> You don’t have access to the history of the variables AFAICT

It seems like you do. [Here is an example](https://docs.sciml.ai/NeuralPDE/stable/tutorials/integro_diff/) from NeuralPDE of solving an integro differential equation.

 ![Screenshot 2026-07-10 at 12.14.45 PM](https://global.discourse-cdn.com/julialang/original/3X/4/9/4941012f82bca8a0c985a021b8c4067521286cc7.png)

---

<div class="post-metadata">

### Author: ![mark.garnett](https://avatars.discourse-cdn.com/v4/letter/m/b9bd4f/32.png) [@mark.garnett](https://discourse.julialang.org/u/mark.garnett)
#### Post date: [July 10, 2026, 6:22pm UTC](https://discourse.julialang.org/t/how-to-use-a-convolution-integral-with-neuralpde-discretize/137997/8 "2026-07-10T18:22:56Z")

</div>

Great! Thank you. I’ll see if I can make it work for the problem I was trying to solve.

---

<div class="post-metadata">

### Author: ![baez-rafael](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/baez-rafael/32/222377_2.png) [@baez-rafael](https://discourse.julialang.org/u/baez-rafael)
#### Post date: [July 10, 2026, 6:39pm UTC](https://discourse.julialang.org/t/how-to-use-a-convolution-integral-with-neuralpde-discretize/137997/9 "2026-07-10T18:39:11Z")

</div>

Briefly reading through [NeuralPDE’s paper](https://arxiv.org/pdf/2107.09443), the section describing Integro-Differential Equations gives an answer to how NeuralPDE.jl handles the history problem.

“Because the neural network defines the value of 𝑢(𝑥) over all space, one can simply use a quadrature technique, such as those in Quadrature.jl , to evaluate the current value of the integral and thus utilize these terms within the PDE equations.”

While the paper is outdated, the example that @cmichelenstrofer gave is from the up-to-date docs. In that case this should be a syntax issue then, @mark.garnett let us know if you have better luck than I did when writing the equation for your problem!

---

<div class="post-metadata">

### Author: ![ChrisRackauckas](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/chrisrackauckas/32/77_2.png) [@ChrisRackauckas](https://discourse.julialang.org/u/ChrisRackauckas)
#### Post date: [September 9, 2026, 9:53am UTC](https://discourse.julialang.org/t/how-to-use-a-convolution-integral-with-neuralpde-discretize/137997/10 "2026-09-09T09:53:13Z")

</div>

Yeah this was a bug, now solved in [Support locally bound variables in PINN integrals - Pull Request #1149 - SciML/NeuralPDE.jl - GitHub](https://github.com/SciML/NeuralPDE.jl/pull/1149)
