Hello. I am attempting to implement Nitsche method for general boundary conditions from a paper by Juntunen and Stenberg, and my first step is to reproduce Nitsche method for Dirichlet boundary conditions. I found an old tutorial by Dokkens and have successfully translated the code to latest version of dolfinx. However, I’m struggling to understand the origin of the term u_D
and the linked “fundamentals” markdown is broken so I cannot see the definition of the problem that is being solved in the nitsche notebook. Could someone guide me to an implementation of Nitsche’s method for simple Dirichlet boundary conditions (e.g. u(x=0, y) = 1
, u(x=Lx, y) = 0
and u(x, y=0) = u(x, y=Ly) = 0
)?
Here’s my translation of the Nitsche’s demo in the linked notebook but without the pyvista visualization.
import dolfinx
import numpy as np
import pyvista
import ufl
from dolfinx import cpp, fem, io, mesh, plot
from mpi4py import MPI
from petsc4py import PETSc
from ufl import (div, dx, ds, grad, inner, grad)
comm = MPI.COMM_WORLD
N = 8
domain = mesh.create_unit_square(comm, N, N)
V = fem.FunctionSpace(domain, ("CG", 1))
uD = fem.Function(V)
uD.interpolate(lambda x: 1 + x[0] ** 2 + 2 * x[1] ** 2)
uD.x.scatter_forward()
x = ufl.SpatialCoordinate(domain)
n = ufl.FacetNormal(domain)
f = -div(grad(1 + x[0] ** 2 + 2 * x[1] ** 2))
u = ufl.TrialFunction(V)
v = ufl.TestFunction(V)
h = 2 * ufl.Circumradius(domain)
alpha = 10
a = inner(grad(u), grad(v)) * dx - inner(n, grad(u)) * v * ds
a += - inner(n, grad(v)) * u * ds + alpha / h * inner(u, v) * ds
L = inner(f, v) * dx
L += - inner(n, grad(v)) * uD * ds + alpha / h * inner(uD, v) * ds
problem = fem.petsc.LinearProblem(a, L)
uh = problem.solve()
with io.XDMFFile(comm, "nitsche.xdmf", "w") as outfile:
outfile.write_mesh(domain)
outfile.write_function(uh)
error_form = fem.form(inner(uh - uD, uh - uD) * dx)
errorL2 = np.sqrt(fem.assemble_scalar(error_form))
print(fr"$L^2$-error: {errorL2:.2e}")
u_vertex_values = uh.x.array.real
u_ex_vertex_values = uD.x.array.real
error_max = np.max(np.abs(u_vertex_values - u_ex_vertex_values))
print(f"Error_max : {error_max:.2e}")
Thank you for any help.