There is a test case, a vector-valued problem on (0, 1)
\begin{cases}
\frac{\partial u_1}{\partial t} &= \frac{\partial^2 u_1}{\partial x^2} - \exp(u_1 - u_2) + \exp(-(u_1 - u_2)) \\
\frac{\partial u_2}{\partial t} &= \frac{\partial^2 u_2}{\partial x^2} + \exp(u_1 - u_2) - \exp(-(u_1 - u_2)) \\
\end{cases}
the boundary condition is
\begin{cases}
\frac{\partial u_1}{\partial x}(0, t) &= \sin(u_1(x = 0)) \\
\frac{\partial u_2}{\partial x}(0, t) &= -0.1u_1(x=0)u_2(x=0)
\end{cases}
\quad
\begin{cases}
u_1(1, t) = 1 \\
u_2(1, t) = 0
\end{cases}
# -*- coding:utf-8 -*-
import ufl
import dolfinx
from dolfinx.fem.petsc import NonlinearProblem
from dolfinx.nls.petsc import NewtonSolver
from petsc4py import PETSc
from mpi4py import MPI
import numpy as np
t_ini = 0
t_fin = 1.1
n_step = 11
dt = (t_fin - t_ini) / n_step
nx = 64
L = 1.0
rank = MPI.COMM_WORLD.Get_rank()
domain = dolfinx.mesh.create_interval(MPI.COMM_WORLD, nx, points=(0.0, L))
V = dolfinx.fem.FunctionSpace(domain, ufl.VectorElement("Lagrange", domain.ufl_cell(), 1, dim=2))
fdim = domain.topology.dim - 1
boundary_facets = dolfinx.mesh.locate_entities_boundary(domain, fdim, lambda x: np.isclose(L, x[0]))
bc1 = dolfinx.fem.dirichletbc(PETSc.ScalarType(1.0),
dolfinx.fem.locate_dofs_topological(V.sub(0), fdim, boundary_facets),
V.sub(0))
bc2 = dolfinx.fem.dirichletbc(PETSc.ScalarType(0.0),
dolfinx.fem.locate_dofs_topological(V.sub(1), fdim, boundary_facets),
V.sub(1))
u_n = dolfinx.fem.Function(V)
u = dolfinx.fem.Function(V)
u_n1, u_n2 = ufl.split(u_n)
u1, u2 = ufl.split(u)
u_n.sub(0).interpolate(lambda x: np.ones(x[0].shape))
u_n.sub(1).interpolate(lambda x: np.zeros(x[0].shape))
u_n.x.scatter_forward()
v1, v2 = ufl.TestFunction(V)
G = -ufl.exp(u1-u2)+ufl.exp(-(u1-u2))
F1 = u1*v1*ufl.dx + dt*ufl.dot(ufl.grad(u1), ufl.grad(v1))*ufl.dx + dt*ufl.sin(u1)*v1*ufl.ds - dt*G*v1*ufl.dx - u_n1*v1*ufl.dx
F2 = u2*v2*ufl.dx + dt*ufl.dot(ufl.grad(u2), ufl.grad(v2))*ufl.dx + dt*(-0.1*u1*u2)*v2*ufl.ds + dt*G*v2*ufl.dx - u_n2*v2*ufl.dx
F = F1 + F2
problem = NonlinearProblem(F, u, bcs=[bc1, bc2])
solver = NewtonSolver(MPI.COMM_WORLD, problem)
solver.convergence_criterion = "residual"
solver.rtol = 1e-6
ksp = solver.krylov_solver
opts = PETSc.Options()
option_prefix = ksp.getOptionsPrefix()
opts[f"{option_prefix}ksp_type"] = "cg"
opts[f"{option_prefix}pc_type"] = "gamg"
opts[f"{option_prefix}pc_factor_mat_solver_type"] = "mumps"
ksp.setFromOptions()
file = dolfinx.io.XDMFFile(MPI.COMM_WORLD, "diffu_test3/u_tot.xdmf", "w")
file.write_mesh(domain)
t = t_ini
while t < t_fin:
n, converged = solver.solve(u)
if (rank == 0):
print(f"Number of interations: {n:d}")
u_n.x.array[:] = u.x.array
file.write_function(u, t)
t += dt
file.close()