every part builds on the one before. New to the topic? Start at part 01.
What a solution operator is, and what actually separates a neural operator from a normal network
Post 4 built a network that steps the wave equation forward in time, and ended by naming resolution-independent neural-operator methods as something it would not go into. This post goes into it. It starts with the mathematical object these networks are trying to approximate, then states the one property that separates a neural operator from the network of Post 4, and then works through DeepONet as the first architecture built around that property.
Take the wave equation from Post 3 with an initial condition. Post 4 showed that displacement alone does not determine a wave's future, so the initial condition consists of two fields, displacement and velocity, given over the whole domain. Call that pair
Given
where
It is called an operator instead of a function because its input and its output are both entire functions rather than numbers. That is the whole meaning of the word here.
Three things have to be true before the operator is even well defined, and together they are called well-posedness: a solution has to exist for every input we allow, it has to be the only one, and a small change to the input has to cause only a small change to the output. The third one is stability, and it is the one that tends to fail for inverse problems, where the task is to recover a cause from measured effects. That is why inverse methods usually cannot get away with returning a single answer and have to report uncertainty as well.
The symplectic Euler scheme from Post 6 does not compute
A network trained on PDE data is doing the same thing from a different direction. It approximates the same
Both the Post 4 network and DeepONet approximate a solution operator. That is not what distinguishes them, so something else has to.
It is not that one works on continuous data and the other does not. Every network that runs on a computer reads and writes finite arrays of numbers. Nothing about a neural operator stores a continuous function or evaluates an integral exactly. When the general definition of a neural operator layer is written with an integral over the domain, that integral is turned into a finite sum before anything executes. Working with functions describes the object being approximated, never the bytes going through the model.
The real difference is what the learned weights are attached to.
The input layer of the Post on the Neural PDE utilizing the Euler rollout has one slot per grid point per field. Slot 47 is wired to grid point
Sample the same physical field at four times the resolution and the input vector no longer fits. The extra values cannot be padded or dropped, because they are not additional information about the old locations, they are information about new locations the network has no slots for. Retraining from scratch is the only option. The same limitation cuts the other way on the output side: there is no way to ask this network for the displacement halfway between two grid points, because a coordinate that is not one of the
A neural operator attaches its weights to a fixed number of objects whose count does not depend on the grid. In DeepONet those objects are learned basis functions. In the Fourier Neural Operator they are frequency modes. Either way, changing the discretisation or resolution does not change how many weights there are or what each one means, so the trained parameters stay valid.
The simplest objects of this kind are whole shapes spread over the domain. For a string of length 1 m fixed at both ends, as in Post 3, a natural choice is the sine shapes
Where
Each term of the sum is a strip of width
Where
The property this buys is called discretisation invariance: the same trained weights keep working as the discretisation changes, and the predictions get better rather than breaking as it gets finer. That is the actual definition, and the payoff is flexibility. Train once, evaluate at whatever resolution the application needs.
One thing to keep in mind before moving on: discretisation invariance is not a single switch that is either on or off. It can hold on the input side, on the output side, or on both, and most architectures do not have both. DeepONet, which the rest of this post covers, has it on the output side only, which resulted in many additional papers that tried to fix the input side.
Answering one question about a solution takes two pieces of information, and they are not alike.
The first is which initial condition the question is about. On a 100 by 100 grid with two fields that is
The second is where the answer is wanted: a coordinate
DeepONet gives each of them its own sub-network. The branch network takes the 20,000 numbers describing the initial condition. The trunk network takes the coordinate. Both are ordinary feedforward networks, meaning stacks of linear layers with a nonlinear activation in between.
Both sub-networks end in the same number of output neurons, and the prediction is their dot product:
where
So let's unpack what this formula means. First of all, this is a linear combination of the trunk outputs, with the branch outputs as coefficients. The trunk
Now that we have the learned basis, we need to know how to combine them to get the final output. This is where the branch network comes in. The branch network takes in the initial condition
Assuming we
Putting the initial condition and the coordinate into one 20,003-input network would also give something that accepts any query point, so the split needs a reason. There are two.
The first is cost. The branch runs once per initial condition, and its
The second is that the two inputs do different jobs. One says which function we are talking about, the other says where in the output we want to look. Splitting them puts that distinction into the architecture instead of hoping gradient descent works it out.
One training example is a triplet: an initial condition, a query coordinate, and the true value there.
where
What makes this affordable is that one solver run yields many triplets. A single run produces the whole solution field over the whole domain and every saved time, and sampling that field at a few hundred scattered coordinates gives a few hundred training examples that share one expensive run and one branch input. Ten thousand training points can come from a hundred runs.
The trunk takes a coordinate as an actual number, so any point in the domain can be asked for, including points between grid points and points at a resolution never used in training. The output side is genuinely free of the grid.
The branch is not. It is an ordinary feedforward network with one input slot per sensor location, those locations are fixed when the dataset is built, and they have to be identical for every input function the model ever sees. Feeding it an initial condition sampled on a 200 by 200 grid fails for exactly the same reason the Post 4 network fails, and in exactly the same way.
So measured against the definition given earlier, DeepONet satisfies discretisation invariance on one side and not the other. This is a known limitation rather than a technicality, and it is the specific gap that later variants were built to close.
The trunk is made of linear layers and smooth activations, so nearby coordinates give nearby outputs. Across most of a solution field that is what you want, and it is why the trunk interpolates sensibly between training points.
At a wavefront it is the wrong behaviour. Just ahead of the front the displacement is near zero and just behind it is large, so two coordinates a fraction of a cell apart carry very different true values. The basis has to be steep exactly there and flat nearly everywhere else. Networks are bad at this, and the reason for that is spectral bias, which is the tendency of neural networks to fit low-frequency structure first and to struggle to produce sharp local variation at all.
The Fourier Neural Operator attaches its weights to a fixed number of frequency modes instead of to grid positions or to a learned basis. That gives discretisation invariance on both sides rather than one, and by the result above it handles sharp fronts far better.