def test_memoize(): '''Sanity for momoization of translated expressions''' mesh = UnitIntervalMesh(1000) check = lambda a, b: sqrt( abs(assemble(inner(a - b, a - b) * dx(domain=mesh)))) < 1E-10 x, y, z, t = sp.symbols('x y z t') f = 3 * x + t df = Expression(f, degree=1) df.t = 2. # Set DEG = 10 # Degree for the final expression; high to get accuracy # NOTE: e belov can be realized as Expression('df...', df=df) but # this does not allow e.g. using derivatives. So we are slightly # more general subs = {df: f} e = df**2 for e in range(10): e += df**2 e_ = Expression(e, subs=subs, degree=DEG) assert check(e, e_) assert len(subs) == 1 # keys: f, df**2, e but we do subs on copy
def test_conditional(): ''' Let f a sympy polynomial expression, df = Expression(f), v = interpolate(f, V) where V is a suitable polynomial space. If e=e(v) is a UFL expression then Expression(e, {v: f}) should be very close. ''' check = lambda a, b: sqrt(abs(assemble(inner(a-b, a-b)*dx))) < 1E-10 x, y, z, t = sp.symbols('x y z t') f = 3*x + t df = Expression(f, degree=1) df.t = 2. mesh = UnitIntervalMesh(1000) V = FunctionSpace(mesh, 'CG', 1) v = interpolate(df, V) DEG = 10 # Degree for the final expression; high to get accuracy e = conditional(ge(v + 3*v, v), v**2, sin(v)) e_ = Expression(e, subs={v: f}, degree=DEG) e_.t = 2. assert check(e, e_) e = conditional(ufl.operators.And(gt(v + 2, v), lt(v**2, 3)), v**2, v) e_ = Expression(e, subs={v: f}, degree=DEG) e_.t = 2. assert check(e, e_)
def test_nosympy_const_expr(): mesh = UnitSquareMesh(3, 3) a = Constant(3) x, y = SpatialCoordinate(mesh) f = a*(x + 2*y) a_ = sp.Symbol('a') # The idea here to say to compile f effectively into # a*(x[0] + x[1]), a=parameter (see the name of the symbol) fe = Expression(f, subs={a: a_}, degree=1, a=2) # Then we can to refer to it fe.a = 4 check = lambda a, b: sqrt(abs(assemble(inner(a-b, a-b)*dx))) < 1E-10 a.assign(Constant(4)) assert check(f, fe)
def test_collect_expr_params(): '''If Expression with params is substituted pick its params''' mesh = UnitIntervalMesh(1000) check = lambda a, b: sqrt(abs(assemble(inner(a-b, a-b)*dx(domain=mesh)))) < 1E-10 x, y, z, t = sp.symbols('x y z t') f = 3*x + t df = Expression(f, degree=1) df.t = 2. # Set DEG = 10 # Degree for the final expression; high to get accuracy # NOTE: e belov can be realized as Expression('df...', df=df) but # this does not allow e.g. using derivatives. So we are slightly # more general e = df + 3*df e_ = Expression(e, subs={df: f}, degree=DEG) assert check(e, e_)
def test_dnosympy_expr(): check = lambda a, b: sqrt(abs(assemble(inner(a-b, a-b)*dx))) < 1E-10 mesh = UnitSquareMesh(3, 3) x, y = SpatialCoordinate(mesh) f = grad(x*y) fe = Expression(f, degree=1) assert check(f, fe)
def test_nosympy_fconst_expr(): mesh = UnitSquareMesh(3, 3) a, b = Constant(3), Constant(4) x, y = SpatialCoordinate(mesh) z = sin(a+b) f = z*(x + 2*y) a_, b_ = sp.symbols('a, b') # The idea here to say to compile f effectively into # a*(x[0] + x[1]), a=parameter (see the name of the symbol) fe = Expression(f, subs={a: a_, b: b_}, degree=1, a=1, b=1) # Then we can to refer to it fe.a = 4 fe.b = 2 check = lambda a, b: sqrt(abs(assemble(inner(a-b, a-b)*dx))) < 1E-10 a.assign(Constant(4)) b.assign(Constant(2)) assert check(f, fe)
def test_nosympy_const_tensor_expr(): mesh = UnitSquareMesh(3, 3) x, y = SpatialCoordinate(mesh) M = as_matrix(((x, y), (2*y, -x))) A = Constant(((1, 2), (3, 4))) A_ = sp.MatrixSymbol('A', *A.ufl_shape) f = dot(M, A) # Substituting with tensor symbol A we will have # access to its compontents ... fe = Expression(f, degree=1, subs={A: A_}) check = lambda a, b: sqrt(abs(assemble(inner(a-b, a-b)*dx))) < 1E-10 A.assign(Constant(((2, 3), (4, 5)))) assert not check(f, fe) # ... and thus change A fe.A_00, fe.A_01, fe.A_10, fe.A_11 = 2, 3, 4, 5 assert check(f, fe)
def nonlinear_babuska(N, u_exact, p_exact): '''MMS for the problem''' mesh = UnitSquareMesh(N, N) bmesh = BoundaryMesh(mesh, 'exterior') V = FunctionSpace(mesh, 'CG', 1) Q = FunctionSpace(bmesh, 'CG', 1) W = (V, Q) up = ii_Function(W) u, p = up # Split v, q = list(map(TestFunction, W)) Tu, Tv = (Trace(x, bmesh) for x in (u, v)) dxGamma = Measure('dx', domain=bmesh) # Nonlinearity nl = lambda u: (1 + u)**2 f_exact = -div(nl(u) * grad(u)) g_exact = u f = interpolate(Expression(f_exact, subs={u: u_exact}, degree=1), V) h = interpolate(Expression(g_exact, subs={u: u_exact}, degree=4), Q) # The nonlinear functional F = [ inner(nl(u) * grad(u), grad(v)) * dx + inner(p, Tv) * dxGamma - inner(f, v) * dx, inner(Tu, q) * dxGamma - inner(h, q) * dxGamma ] dF = block_jacobian(F, up) return F, dF, up
def test_ufl_mms_2d(): ''' Let f a sympy polynomial expression, df = Expression(f), v = interpolate(f, V) where V is a suitable polynomial space. If e=e(v) is a UFL expression then Expression(e, {v: f}) should be very close. ''' check = lambda a, b: sqrt(abs(assemble(inner(a-b, a-b)*dx))) < 1E-8 x, y, z, t = sp.symbols('x y z t') T = 1.2 f = 3*x*y + x**2 + 2*y**2 + t**3 df = Expression(f, degree=2) df.t = T g = x+y dg = Expression(g, degree=1) mesh = UnitSquareMesh(64, 64) V = FunctionSpace(mesh, 'CG', 2) v = interpolate(df, V) u = interpolate(dg, V) DEG = 6 # Degree for the final expression; high to get accuracy e = u + v e_ = Expression(e, subs={v: f, u: g}, degree=DEG) e_.t = T assert check(e, e_) e = u.dx(0) + v.dx(1) e_ = Expression(e, subs={v: f, u: g}, degree=DEG) e_.t = T assert check(e, e_) e = grad(u) + grad(v) e_ = Expression(e, subs={v: f, u: g}, degree=DEG) e_.t = T assert check(e, e_) e = div(grad(u)) + div(grad(v)) e_ = Expression(e, subs={v: f, u: g}, degree=DEG) e_.t = T assert check(e, e_) uv = as_vector((u, v)) e = grad(grad(u+v)) + outer(uv, uv) e_ = Expression(e, subs={v: f, u: g}, degree=DEG) e_.t = T assert check(e, e_) e = inner(grad(u), grad(v)) e_ = Expression(e, subs={v: f, u: g}, degree=DEG) e_.t = T assert check(e, e_) e = grad(u) + nabla_grad(v) e_ = Expression(e, subs={v: f, u: g}, degree=DEG) e_.t = T assert check(e, e_) uv = as_vector((u, v)) e = grad(nabla_grad(u+v)) + outer(uv, uv) e_ = Expression(e, subs={v: f, u: g}, degree=DEG) e_.t = T assert check(e, e_) e = inner(nabla_grad(u), nabla_grad(v)) e_ = Expression(e, subs={v: f, u: g}, degree=DEG) e_.t = T assert check(e, e_) uv = as_vector((u, v)) e = det(grad(grad(u+v)))# + tr(outer(uv, 2*uv)) e_ = Expression(e, subs={v: f, u: g}, degree=DEG) e_.t = T assert check(e, e_) uv = as_vector((u, v)) e = uv e_ = Expression(e, subs={v: f, u: g}, degree=DEG) e_.t = T assert check(e, e_) e = tr(outer(uv, 2*uv)) e_ = Expression(e, subs={v: f, u: g}, degree=DEG) e_.t = T assert check(e, e_) e = det(outer(uv, 2*uv)) e_ = Expression(e, subs={v: f, u: g}, degree=DEG) e_.t = T assert check(e, e_) e = 2*uv e_ = Expression(e, subs={v: f, u: g}, degree=DEG) e_.t = T assert check(e, e_) e = curl(u) + 2*curl(v) e_ = Expression(e, subs={v: f, u: g}, degree=DEG) e_.t = T assert check(e, e_) e = curl(grad(u*u)) + 2*curl(grad(v*u)) e_ = Expression(e, subs={v: f, u: g}, degree=DEG) e_.t = T assert check(e, e_) x, y = SpatialCoordinate(mesh) e = curl(as_vector((-y**2, x**2))) e_ = Expression(e, subs={v: f, u: g}, degree=DEG) e_.t = T assert check(e, e_) e = div(outer(uv, 2*uv)) e_ = Expression(e, subs={v: f, u: g}, degree=DEG) e_.t = T assert check(e, e_)
def mortar_lin_couple(N): '''...''' interior = CompiledSubDomain( 'std::max(fabs(x[0] - 0.5), fabs(x[1] - 0.5)) < 0.25') outer_mesh = UnitSquareMesh(N, N) subdomains = MeshFunction('size_t', outer_mesh, outer_mesh.topology().dim(), 0) # Awkward marking for cell in cells(outer_mesh): x = cell.midpoint().array() subdomains[cell] = int(interior.inside(x, False)) assert sum(1 for _ in SubsetIterator(subdomains, 1)) > 0 inner_mesh = SubMesh(outer_mesh, subdomains, 1) outer_mesh = SubMesh(outer_mesh, subdomains, 0) # Interior boundary surfaces = MeshFunction('size_t', inner_mesh, inner_mesh.topology().dim() - 1, 0) DomainBoundary().mark(surfaces, 1) gamma_mesh = EmbeddedMesh(surfaces, 1) # --- V1 = FunctionSpace(inner_mesh, 'CG', 1) V2 = FunctionSpace(outer_mesh, 'CG', 1) Q = FunctionSpace(gamma_mesh, 'CG', 1) W = (V1, V2, Q) w = ii_Function(W) u1, u2, p = w # Split v1, v2, q = list(map(TestFunction, W)) Tu1, Tv1 = (Trace(x, gamma_mesh) for x in (u1, v1)) Tu2, Tv2 = (Trace(x, gamma_mesh) for x in (u2, v2)) dxGamma = Measure('dx', domain=gamma_mesh) # Nonlinearity nl1 = lambda u: (1 + u)**2 nl2 = lambda u: (2 + u)**4 f1 = interpolate(Expression('x[0]*x[0]+x[1]*x[1]', degree=1), V1) f2 = interpolate(Constant(1), V2) h = interpolate(Expression('x[0] + x[1]', degree=1), Q) # The nonlinear functional F = [ inner(nl1(u1) * grad(u1), grad(v1)) * dx + inner(u1, v1) * dx + inner(p, Tv1) * dxGamma - inner(f1, v1) * dx, inner(nl2(u2) * grad(u2), grad(v2)) * dx + inner(u2, v2) * dx - inner(p, Tv2) * dxGamma - inner(f2, v2) * dx, inner(Tu1, q) * dxGamma - inner(Tu2, q) * dxGamma - inner(h, q) * dxGamma ] dF = block_jacobian(F, w) # Newton eps = 1.0 tol = 1.0E-10 niter = 0 maxiter = 25 dw = ii_Function(W) while eps > tol and niter < maxiter: niter += 1 A, b = list(map(ii_assemble, (dF, F))) A, b = list(map(ii_convert, (A, b))) solve(A, dw.vector(), b) eps = sqrt(sum(x.norm('l2')**2 for x in dw.vectors())) print('\t%d |du| = %.6E |A|= %.6E |b| = %.6E' % (niter, eps, A.norm('linf'), b.norm('l2'))) # FIXME: Update for i in range(len(W)): w[i].vector().axpy(-1, dw[i].vector()) return w
def nonlinear_babuska(N, u_exact, p_exact): '''MMS for the problem''' mesh = UnitSquareMesh(N, N) bmesh = BoundaryMesh(mesh, 'exterior') V = FunctionSpace(mesh, 'CG', 1) Q = FunctionSpace(bmesh, 'CG', 1) W = (V, Q) up = ii_Function(W) u, p = up # Split v, q = list(map(TestFunction, W)) Tu, Tv = (Trace(x, bmesh) for x in (u, v)) dxGamma = Measure('dx', domain=bmesh) # Nonlinearity nl = lambda u: (1 + u)**2 f_exact = -div(nl(u) * grad(u)) g_exact = u f = interpolate(Expression(f_exact, subs={u: u_exact}, degree=1), V) h = interpolate(Expression(g_exact, subs={u: u_exact}, degree=4), Q) # The nonlinear functional F = [ inner(nl(u) * grad(u), grad(v)) * dx + inner(p, Tv) * dxGamma - inner(f, v) * dx, inner(Tu, q) * dxGamma - inner(h, q) * dxGamma ] dF = block_jacobian(F, up) # Newton eps = 1.0 tol = 1.0E-10 niter = 0 maxiter = 25 OptDB = PETSc.Options() # This is way to use inv(A) for the solution OptDB.setValue('ksp_type', 'preonly') # Only appy preconditiner # Which is lu factorization with umfpack. NOTE: the package matters # a lot; e.g. superlu_dist below blows up OptDB.setValue('pc_type', 'lu') OptDB.setValue('pc_factor_mat_solver_package', 'umfpack') dup = ii_Function(W) x_vec = as_backend_type(dup.vector()).vec() while eps > tol and niter < maxiter: niter += 1 A, b = (ii_convert(ii_assemble(x)) for x in (dF, F)) # PETSc solver A_mat = as_backend_type(A).mat() b_vec = as_backend_type(b).vec() ksp = PETSc.KSP().create() ksp.setOperators(A_mat) ksp.setFromOptions() ksp.solve(b_vec, x_vec) niters = ksp.getIterationNumber() # DOLFIN solver # niters = solve(A, dup.vector(), b) eps = sqrt(sum(x.norm('l2')**2 for x in dup.vectors())) print('\t%d |du| = %g |A|= %g |b| = %g | niters %d' % (niter, eps, A.norm('linf'), b.norm('l2'), niters)) # FIXME: Update for i in range(len(W)): up[i].vector().axpy(-1, dup[i].vector()) return up
return up, n_kspiters # -------------------------------------------------------------------- if __name__ == '__main__': import sympy as sp RED = '\033[1;37;31m%s\033[0m' # Setup the test case x, y = sp.symbols('x y') u_exact = sp.cos(sp.pi * x * (1 - x) * y * (1 - y)) p_exact = sp.S(0) u_expr = Expression(u_exact, degree=4) p_expr = Expression(p_exact, degree=4) eu0, ep0, h0 = -1, -1, -1 for N in (8, 16, 32, 64, 128, 256, 512, 1024): (uh, ph), niters = nonlinear_babuska(N, u_exact, p_exact) Vh = uh.function_space() Qh = ph.function_space() eu = errornorm(uh, u_expr, 'H1', degree_rise=0) ep = errornorm(ph, p_expr, 'L2', degree_rise=0) h = Vh.mesh().hmin() if eu0 > 0: rate_u = ln(eu / eu0) / ln(h / h0) rate_p = ln(ep / ep0) / ln(h / h0)
def test_diff(): '''Sanity check for VaraibleDerivative''' check = lambda a, b: sqrt(abs(assemble(inner(a-b, a-b)*dx))) < 1E-8 x, y, z, t = sp.symbols('x y z t') T = 1.2 f = 3*x*y + x**2 + 2*y**2 + t**3 df = Expression(f, degree=2) df.t = T g = x+y dg = Expression(g, degree=1) mesh = UnitSquareMesh(64, 64) V = FunctionSpace(mesh, 'CG', 2) v = interpolate(df, V) u = interpolate(dg, V) DEG = 6 # Degree for the final expression; high to get accuracy u_, v_ = list(map(variable, (u, v))) e = diff(u_**2 + v_**2, u_) e_ = Expression(e, subs={v: f, u: g}, degree=DEG) e_.t = T assert check(e, e_) u_, v_ = list(map(variable, (u, v))) e = diff(u_**2 + v_**2, u_) e_ = Expression(e, subs={v_: f, u_: g}, degree=DEG) e_.t = T assert check(e, e_) u_, v_ = list(map(variable, (u, v))) e = u**2 - v.dx(0) + diff(u_**2 + v_**2, u_) e_ = Expression(e, subs={v_: f, u_: g}, degree=DEG) e_.t = T assert check(e, e_)
def test_ufl_mms_1d(): ''' Let f a sympy polynomial expression, df = Expression(f), v = interpolate(f, V) where V is a suitable polynomial space. If e=e(v) is a UFL expression then Expression(e, {v: f}) should be very close. ''' check = lambda a, b: sqrt(abs(assemble(inner(a-b, a-b)*dx))) < 1E-10 x, y, z, t = sp.symbols('x y z t') f = 3*x + t df = Expression(f, degree=1) df.t = 2. # Old expression still works Expression('x[0]+1', degree=1) mesh = UnitIntervalMesh(1000) V = FunctionSpace(mesh, 'CG', 1) v = interpolate(df, V) DEG = 10 # Degree for the final expression; high to get accuracy e = v + 3*v e_ = Expression(e, subs={v: f}, degree=DEG) e_.t = 2. assert check(e, e_) e = v - 3*v**2 e_ = Expression(e, subs={v: f}, degree=DEG) e_.t = 2. assert check(e, e_) e = v - 3*v**2 + v.dx(0) e_ = Expression(e, subs={v: f}, degree=DEG) e_.t = 2. assert check(e, e_) e = v - 3*v**2 + sin(v).dx(0) e_ = Expression(e, subs={v: f}, degree=DEG) e_.t = 2. assert check(e, e_) e = v - 3*v**2 + cos(v)*v.dx(0) e_ = Expression(e, subs={v: f}, degree=DEG) e_.t = 2. assert check(e, e_)
def nonlinear_babuska(N, u_exact, p_exact): '''MMS for the problem''' mesh = UnitSquareMesh(N, N) bmesh = BoundaryMesh(mesh, 'exterior') V = FunctionSpace(mesh, 'CG', 1) Q = FunctionSpace(bmesh, 'CG', 1) W = (V, Q) up = ii_Function(W) u, p = up # Split v, q = list(map(TestFunction, W)) Tu, Tv = (Trace(x, bmesh) for x in (u, v)) dxGamma = Measure('dx', domain=bmesh) # Nonlinearity nl = lambda u: (Constant(2) + u)**2 f_exact = -div(nl(u) * grad(u)) g_exact = u f = interpolate(Expression(f_exact, subs={u: u_exact}, degree=1), V) h = interpolate(Expression(g_exact, subs={u: u_exact}, degree=4), Q) # The nonlinear functional F = [ inner(nl(u) * grad(u), grad(v)) * dx + inner(p, Tv) * dxGamma - inner(f, v) * dx, inner(Tu, q) * dxGamma - inner(h, q) * dxGamma ] dF = block_jacobian(F, up) # Setup H1 x H-0.5 preconditioner only once B0 = ii_derivative(inner(grad(u), grad(v)) * dx + inner(u, v) * dx, u) # The Q norm via spectral B1 = inverse(HsNorm(Q, s=-0.5)) # The norm is inverted exactly # Preconditioner B = block_diag_mat([AMG(ii_assemble(B0)), B1]) # Newton eps = 1.0 tol = 1.0E-10 niter = 0. maxiter = 25 OptDB = PETSc.Options() # Since later b gets very small making relative too much work OptDB.setValue('ksp_atol', 1E-6) OptDB.setValue('ksp_monitor_true_residual', None) dup = ii_Function(W) x_vec = as_backend_type(dup.vector()).vec() n_kspiters = [] while eps > tol and niter < maxiter: niter += 1. A, b = (ii_assemble(x) for x in (dF, F)) ksp = PETSc.KSP().create() ksp.setType('minres') ksp.setNormType(PETSc.KSP.NormType.NORM_PRECONDITIONED) ksp.setOperators(ii_PETScOperator(A)) ksp.setPC(ii_PETScPreconditioner(B, ksp)) ksp.setFromOptions() ksp.solve(as_petsc_nest(b), x_vec) niters = ksp.getIterationNumber() + 1 n_kspiters.append(niters) eps = sqrt(sum(x.norm('l2')**2 for x in dup.vectors())) print('\t%d |du| = %g | niters %d' % (niter, eps, niters)) # FIXME: Update for i in range(len(W)): up[i].vector().axpy(-1, dup[i].vector()) return up, n_kspiters
def test_ufl_mms_2d_mat(): ''' Let f a sympy polynomial expression, df = Expression(f), v = interpolate(f, V) where V is a suitable polynomial space. If e=e(v) is a UFL expression then Expression(e, {v: f}) should be very close. ''' check = lambda a, b: sqrt(abs(assemble(inner(a-b, a-b)*dx))) < 1E-8 x, y, z, t = sp.symbols('x y z t') T = 1.2 f = sp.Matrix([[3*x*y + x**2 + 2*y**2 + t**3, x], [y, x+y]]) df = Expression(f, degree=2) df.t = T g = sp.Matrix([[x+y, 1], [y, -x]]) dg = Expression(g, degree=1) mesh = UnitSquareMesh(32, 32) V = TensorFunctionSpace(mesh, 'CG', 2) v = interpolate(df, V) u = interpolate(dg, V) DEG = 6 e = u + v e_ = Expression(e, subs={v: f, u: g}, degree=DEG) e_.t = T assert check(e, e_) e = inner(u, v) e_ = Expression(e, subs={v: f, u: g}, degree=DEG) e_.t = T assert check(e, e_) R = Constant(((1, 2), (3, 4))) e = R*u e_ = Expression(e, subs={v: f, u: g}, degree=DEG) e_.t = T print(check(e, e_)) e = det(u) e_ = Expression(e, subs={v: f, u: g}, degree=DEG) e_.t = T assert check(e, e_) e = tr(dot(u, v)) e_ = Expression(e, subs={v: f, u: g}, degree=DEG) e_.t = T assert check(e, e_) e = div(u+v) e_ = Expression(e, subs={v: f, u: g}, degree=DEG) e_.t = T assert check(e, e_)
def test_ufl_mms_3d_mat(): ''' Let f a sympy polynomial expression, df = Expression(f), v = interpolate(f, V) where V is a suitable polynomial space. If e=e(v) is a UFL expression then Expression(e, {v: f}) should be very close. ''' mesh = UnitCubeMesh(8, 8, 8) check = lambda a, b: sqrt(abs(assemble(inner(a-b, a-b)*dx(domain=mesh)))) < 1E-8 x, y, z, t = sp.symbols('x y z t') T = 0.123 f = sp.Matrix([[3*x, x, z], [y, x, z], [x, y-y, z]]) df = Expression(f, degree=1) df.t = T g = sp.Matrix([[x+y, 1, x], [y, -x, z], [x+y, y+z, z-x]]) dg = Expression(g, degree=1) V = TensorFunctionSpace(mesh, 'CG', 1) v = interpolate(df, V) u = interpolate(dg, V) DEG = 3 X = Constant(((1, 2), (3, 4))) e = X*X e_ = Expression(e, subs={v: f, u: g}, degree=DEG) e_.t = T assert check(e, e_) e = X*Constant((1, 2)) e_ = Expression(e, subs={v: f, u: g}, degree=DEG) e_.t = T assert check(e, e_) e = X*X[:, 1] e_ = Expression(e, subs={v: f, u: g}, degree=DEG) e_.t = T assert check(e, e_) e = u + v e_ = Expression(e, subs={v: f, u: g}, degree=DEG) e_.t = T assert check(e, e_) e = inner(u, v) e_ = Expression(e, subs={v: f, u: g}, degree=DEG) e_.t = T assert check(e, e_) e = v*u*u e_ = Expression(e, subs={v: f, u: g}, degree=DEG) e_.t = T print(check(e, e_)) e = det(u) e_ = Expression(e, subs={v: f, u: g}, degree=DEG) e_.t = T assert check(e, e_) e = tr(dot(u, v)) e_ = Expression(e, subs={v: f, u: g}, degree=DEG) e_.t = T assert check(e, e_) e = div(u+v) e_ = Expression(e, subs={v: f, u: g}, degree=DEG) e_.t = T assert check(e, e_)
def test_ufl_mms_3d_vec(): ''' Let f a sympy polynomial expression, df = Expression(f), v = interpolate(f, V) where V is a suitable polynomial space. If e=e(v) is a UFL expression then Expression(e, {v: f}) should be very close. ''' check = lambda a, b: sqrt(abs(assemble(inner(a-b, a-b)*dx))) < 1E-8 x, y, z, t = sp.symbols('x y z t') T = 1.2 f = sp.Matrix([3*x*y + x*z + 2*y*z + t**3 + z**2 - x**2, x+y*z, y-z]) df = Expression(f, degree=2) df.t = T g = sp.Matrix([x+y+z, x-y-z, y]) dg = Expression(g, degree=1) mesh = UnitCubeMesh(8, 8, 8) V = VectorFunctionSpace(mesh, 'CG', 2) v = interpolate(df, V) u = interpolate(dg, V) DEG = 3 e = u + v e_ = Expression(e, subs={v: f, u: g}, degree=DEG) e_.t = T assert check(e, e_) e = inner(u, v) e_ = Expression(e, subs={v: f, u: g}, degree=DEG) e_.t = T assert check(e, e_) R = Constant(((1, 2, 0), (0, 3, 4), (0, 0, 1))) e = R*u e_ = Expression(e, subs={v: f, u: g}, degree=DEG) e_.t = T print(check(e, e_)) e = dot(R, u) e_ = Expression(e, subs={v: f, u: g}, degree=DEG) e_.t = T assert check(e, e_) e = dot(v, R) e_ = Expression(e, subs={v: f, u: g}, degree=DEG) e_.t = T assert check(e, e_) e = grad(u+v) e_ = Expression(e, subs={v: f, u: g}, degree=DEG) e_.t = T assert check(e, e_) e = div(u - v) e_ = Expression(e, subs={v: f, u: g}, degree=DEG) e_.t = T assert check(e, e_) e = curl(2*u - 3*v) e_ = Expression(e, subs={v: f, u: g}, degree=DEG) e_.t = T assert check(e, e_)