def test_near_evaluations(R, mesh): # Test that we allow point evaluation that are slightly outside u0 = Function(R) u0.vector.set(1.0) offset = 0.99 * np.finfo(float).eps bb_tree = geometry.BoundingBoxTree(mesh, mesh.geometry.dim) a = mesh.geometry.x[0] cell_candidates = geometry.compute_collisions_point(bb_tree, a) cells = geometry.select_colliding_cells(mesh, cell_candidates, a, 1) a_shift_x = np.array([a[0] - offset, a[1], a[2]]) cell_candidates = geometry.compute_collisions_point(bb_tree, a_shift_x) cells_shift_x = geometry.select_colliding_cells(mesh, cell_candidates, a_shift_x, 1) assert u0.eval(a, cells)[0] == pytest.approx( u0.eval(a_shift_x, cells_shift_x)[0]) a_shift_xyz = np.array([ a[0] - offset / math.sqrt(3), a[1] - offset / math.sqrt(3), a[2] - offset / math.sqrt(3) ]) cell_candidates = geometry.compute_collisions_point(bb_tree, a) cells_shift_xyz = geometry.select_colliding_cells(mesh, cell_candidates, a_shift_xyz, 1) assert u0.eval(a, cells)[0] == pytest.approx( u0.eval(a_shift_xyz, cells_shift_xyz)[0])
def test_eval_multiple(W): u = Function(W) u.vector.set(1.0) mesh = W.mesh x0 = (mesh.geometry.x[0] + mesh.geometry.x[1]) / 2.0 x = np.array([x0, x0 + 1.0e8]) tree = geometry.BoundingBoxTree(mesh, W.mesh.geometry.dim) cells = geometry.compute_first_entity_collision(tree, mesh, x) u.eval(x[0], cells[0])
def test_eval_multiple(W): u = Function(W) u.vector.set(1.0) mesh = W.mesh x0 = (mesh.geometry.x[0] + mesh.geometry.x[1]) / 2.0 x = np.array([x0, x0 + 1.0e8]) tree = geometry.BoundingBoxTree(mesh, mesh.geometry.dim) cell_candidates = [geometry.compute_collisions_point(tree, xi) for xi in x] assert len(cell_candidates[1]) == 0 cell_candidates = cell_candidates[0] cell = dolfinx.cpp.geometry.select_colliding_cells(mesh, cell_candidates, x0, 1) u.eval(x[0], cell)
def xtest_near_evaluations(R, mesh): # Test that we allow point evaluation that are slightly outside bb_tree = cpp.geometry.BoundingBoxTree(mesh, mesh.geometry.dim) u0 = Function(R) u0.vector.set(1.0) a = mesh.geometry.x(0) offset = 0.99 * np.finfo(float).eps a_shift_x = np.array([a[0] - offset, a[1], a[2]]) assert u0.eval(a, bb_tree)[0] == pytest.approx(u0.eval(a_shift_x, bb_tree)[0]) a_shift_xyz = np.array([a[0] - offset / math.sqrt(3), a[1] - offset / math.sqrt(3), a[2] - offset / math.sqrt(3)]) assert u0.eval(a, bb_tree)[0] == pytest.approx(u0.eval(a_shift_xyz, bb_tree)[0])
def test_N2curl_interpolation(cell_type, order): mesh = one_cell_mesh(cell_type) tdim = mesh.topology.dim # TODO: fix higher order elements if tdim == 2 and order > 1: pytest.skip("N2curl order > 1 in 2D needs fixing") V = FunctionSpace(mesh, ("Nedelec 2nd kind H(curl)", order)) v = Function(V) if tdim == 2: def f(x): return (x[1]**order, 2 * x[0]) else: def f(x): return (x[1]**order + 2 * x[0], x[2]**order, -3 * x[2]) v.interpolate(f) points = [random_point_in_cell(cell_type) for count in range(5)] cells = [0 for count in range(5)] values = v.eval(points, cells) assert np.allclose(values, [f(p) for p in points])
def run_vector_test(V, poly_order): """Test that interpolation is correct in a scalar valued space.""" random.seed(12) tdim = V.mesh.topology.dim if tdim == 1: def f(x): return x[0]**poly_order elif tdim == 2: def f(x): return (x[1]**min(poly_order, 1), 2 * x[0]**poly_order) else: def f(x): return (x[1]**min(poly_order, 1), 2 * x[0]**poly_order, 3 * x[2]**min(poly_order, 2)) v = Function(V) v.interpolate(f) points = [random_point_in_cell(V.mesh) for count in range(5)] cells = [0 for count in range(5)] values = v.eval(points, cells) for p, val in zip(points, values): assert np.allclose(val, f(p))
def test_evaluation(cell_type, space_type, space_order): random.seed(4) for repeat in range(10): mesh = random_evaluation_mesh(cell_type) V = FunctionSpace(mesh, (space_type, space_order)) dofs = [i for i in V.dofmap.cell_dofs(0) if i in V.dofmap.cell_dofs(1)] N = 5 if cell_type == "tetrahedron": eval_points = np.array([[0., i / N, j / N] for i in range(N + 1) for j in range(N + 1 - i)]) elif cell_type == "hexahedron": eval_points = np.array([[0., i / N, j / N] for i in range(N + 1) for j in range(N + 1)]) else: eval_points = np.array([[0., i / N, 0.] for i in range(N + 1)]) for d in dofs: v = Function(V) v.vector[:] = [1 if i == d else 0 for i in range(v.vector.local_size)] values0 = v.eval(eval_points, [0 for i in eval_points]) values1 = v.eval(eval_points, [1 for i in eval_points]) if len(eval_points) == 1: values0 = [values0] values1 = [values1] if space_type in ["RT", "BDM", "RTCF", "NCF"]: # Hdiv for i, j in zip(values0, values1): assert np.isclose(i[0], j[0]) elif space_type in ["N1curl", "N2curl", "RTCE", "NCE"]: # Hcurl for i, j in zip(values0, values1): assert np.allclose(i[1:], j[1:]) else: assert np.allclose(values0, values1)
def test_mixed_interpolation(cell_type, order): """Test that interpolation is correct in a MixedElement.""" mesh = one_cell_mesh(cell_type) tdim = mesh.topology.dim A = ufl.FiniteElement("Lagrange", mesh.ufl_cell(), order) B = ufl.VectorElement("Lagrange", mesh.ufl_cell(), order) V = FunctionSpace(mesh, ufl.MixedElement([A, B])) v = Function(V) if tdim == 1: def f(x): return (x[0]**order, 2 * x[0]) elif tdim == 2: def f(x): return (x[1], 2 * x[0]**order, 3 * x[1]) else: def f(x): return (x[1], 2 * x[0]**order, 3 * x[2], 4 * x[0]) v.interpolate(f) points = [random_point_in_cell(cell_type) for count in range(5)] cells = [0 for count in range(5)] values = v.eval(points, cells) for p, v in zip(points, values): assert np.allclose(v, f(p))
def test_scalar_interpolation(cell_type, order): """Test that interpolation is correct in a FunctionSpace""" mesh = one_cell_mesh(cell_type) tdim = mesh.topology.dim V = FunctionSpace(mesh, ("Lagrange", order)) v = Function(V) if tdim == 1: def f(x): return x[0]**order elif tdim == 2: def f(x): return x[1]**order + 2 * x[0] else: def f(x): return x[1]**order + 2 * x[0] - 3 * x[2] v.interpolate(f) points = [random_point_in_cell(cell_type) for count in range(5)] cells = [0 for count in range(5)] values = v.eval(points, cells) for p, v in zip(points, values): assert np.allclose(v, f(p))
def test_manufactured_vector2(family, degree, filename, datadir): """Projection into H(div/curl) spaces""" # Skip slowest tests if "tetra" in filename and degree > 2: return with XDMFFile(MPI.comm_world, os.path.join(datadir, filename)) as xdmf: mesh = xdmf.read_mesh(GhostMode.none) # FIXME: these test are currently failing on unordered meshes if "tetra" in filename: if family == "N1curl": Ordering.order_simplex(mesh) V = FunctionSpace(mesh, (family, degree + 1)) u, v = ufl.TrialFunction(V), ufl.TestFunction(V) a = inner(u, v) * dx xp = np.array([0.33, 0.33, 0.0]) tree = geometry.BoundingBoxTree(mesh, mesh.geometry.dim) cells = geometry.compute_first_entity_collision(tree, mesh, xp) # Source term x = SpatialCoordinate(mesh) u_ref = x[0]**degree L = inner(u_ref, v[0]) * dx b = assemble_vector(L) b.ghostUpdate(addv=PETSc.InsertMode.ADD, mode=PETSc.ScatterMode.REVERSE) A = assemble_matrix(a) A.assemble() # Create LU linear solver (Note: need to use a solver that # re-orders to handle pivots, e.g. not the PETSc built-in LU # solver) solver = PETSc.KSP().create(MPI.comm_world) solver.setType("preonly") solver.getPC().setType('lu') solver.setOperators(A) # Solve uh = Function(V) solver.solve(b, uh.vector) uh.vector.ghostUpdate(addv=PETSc.InsertMode.INSERT, mode=PETSc.ScatterMode.FORWARD) up = uh.eval(xp, cells[0]) print("test0:", up) print("test1:", xp[0]**degree) u_exact = np.zeros(mesh.geometry.dim) u_exact[0] = xp[0]**degree assert np.allclose(up, u_exact)
def test_eval(V, W, Q, mesh): u1 = Function(V) u2 = Function(W) u3 = Function(Q) def e1(x): return x[0] + x[1] + x[2] def e2(x): values = np.empty((3, x.shape[1])) values[0] = x[0] + x[1] + x[2] values[1] = x[0] - x[1] - x[2] values[2] = x[0] + x[1] + x[2] return values def e3(x): values = np.empty((9, x.shape[1])) values[0] = x[0] + x[1] + x[2] values[1] = x[0] - x[1] - x[2] values[2] = x[0] + x[1] + x[2] values[3] = x[0] values[4] = x[1] values[5] = x[2] values[6] = -x[0] values[7] = -x[1] values[8] = -x[2] return values u1.interpolate(e1) u2.interpolate(e2) u3.interpolate(e3) x0 = (mesh.geometry.x[0] + mesh.geometry.x[1]) / 2.0 tree = geometry.BoundingBoxTree(mesh, mesh.geometry.dim) cell_candidates = geometry.compute_collisions_point(tree, x0) cell = dolfinx.cpp.geometry.select_colliding_cells(mesh, cell_candidates, x0, 1) assert np.allclose(u3.eval(x0, cell)[:3], u2.eval(x0, cell), rtol=1e-15, atol=1e-15)
def test_eval_manifold(): # Simple two-triangle surface in 3d vertices = [(0.0, 0.0, 1.0), (1.0, 1.0, 1.0), (1.0, 0.0, 0.0), (0.0, 1.0, 0.0)] cells = [(0, 1, 2), (0, 1, 3)] cell = ufl.Cell("triangle", geometric_dimension=3) domain = ufl.Mesh(ufl.VectorElement("Lagrange", cell, 1)) mesh = create_mesh(MPI.COMM_WORLD, cells, vertices, domain) Q = FunctionSpace(mesh, ("Lagrange", 1)) u = Function(Q) u.interpolate(lambda x: x[0] + x[1]) assert np.isclose(u.eval([0.75, 0.25, 0.5], 0)[0], 1.0)
def test_quadrilateral_evaluation(space_type, space_order): domain = ufl.Mesh(ufl.VectorElement("Lagrange", "quadrilateral", 1)) temp_points = np.array([[-1., -1.], [0., 0.], [1., 0.], [-1., 1.], [0., 1.], [2., 2.]]) for repeat in range(10): order = [i for i, j in enumerate(temp_points)] shuffle(order) points = np.zeros(temp_points.shape) for i, j in enumerate(order): points[j] = temp_points[i] connections = {0: [1, 2], 1: [0, 3], 2: [0, 3], 3: [1, 2]} cells = [] for cell in [[0, 1, 3, 4], [1, 2, 4, 5]]: # Randomly number the cell start = choice(range(4)) cell_order = [start] for i in range(2): diff = choice([ i for i in connections[start] if i not in cell_order ]) - cell_order[0] cell_order += [c + diff for c in cell_order] cells.append([order[cell[i]] for i in cell_order]) mesh = create_mesh(MPI.COMM_WORLD, cells, points, domain) V = FunctionSpace(mesh, (space_type, space_order)) dofs = [i for i in V.dofmap.cell_dofs(0) if i in V.dofmap.cell_dofs(1)] N = 6 eval_points = np.array([[0., i / N, 0.] for i in range(N + 1)]) for d in dofs: v = Function(V) v.vector[:] = [ 1 if i == d else 0 for i in range(v.vector.local_size) ] values0 = v.eval(eval_points, [0 for i in eval_points]) values1 = v.eval(eval_points, [1 for i in eval_points]) if len(eval_points) == 1: values0 = [values0] values1 = [values1] if space_type == "RTCF": # Hdiv for i, j in zip(values0, values1): assert np.isclose(i[0], j[0]) elif space_type == "RTCE": # Hcurl for i, j in zip(values0, values1): assert np.allclose(i[1], j[1]) else: assert np.allclose(values0, values1)
def test_eval_manifold(): # Simple two-triangle surface in 3d vertices = [(0.0, 0.0, 1.0), (1.0, 1.0, 1.0), (1.0, 0.0, 0.0), (0.0, 1.0, 0.0)] cells = [(0, 1, 2), (0, 1, 3)] mesh = Mesh(MPI.COMM_WORLD, cpp.mesh.CellType.triangle, np.array(vertices, dtype=np.float64), np.array(cells, dtype=np.int32), []) Q = FunctionSpace(mesh, ("CG", 1)) u = Function(Q) u.interpolate(lambda x: x[0] + x[1]) assert np.isclose(u.eval([0.75, 0.25, 0.5], 0)[0], 1.0)
def test_manufactured_vector1(family, degree, filename, datadir): """Projection into H(div/curl) spaces""" with XDMFFile(MPI.COMM_WORLD, os.path.join(datadir, filename), "r", encoding=XDMFFile.Encoding.ASCII) as xdmf: mesh = xdmf.read_mesh(name="Grid") V = FunctionSpace(mesh, (family, degree)) u, v = ufl.TrialFunction(V), ufl.TestFunction(V) a = inner(u, v) * dx # Source term x = SpatialCoordinate(mesh) u_ref = x[0]**degree L = inner(u_ref, v[0]) * dx b = assemble_vector(L) b.ghostUpdate(addv=PETSc.InsertMode.ADD, mode=PETSc.ScatterMode.REVERSE) A = assemble_matrix(a) A.assemble() # Create LU linear solver (Note: need to use a solver that # re-orders to handle pivots, e.g. not the PETSc built-in LU # solver) solver = PETSc.KSP().create(MPI.COMM_WORLD) solver.setType("preonly") solver.getPC().setType('lu') solver.setOperators(A) # Solve uh = Function(V) solver.solve(b, uh.vector) uh.vector.ghostUpdate(addv=PETSc.InsertMode.INSERT, mode=PETSc.ScatterMode.FORWARD) xp = np.array([0.33, 0.33, 0.0]) tree = geometry.BoundingBoxTree(mesh, mesh.geometry.dim) cells = geometry.compute_first_entity_collision(tree, mesh, xp) up = uh.eval(xp, cells[0]) print("test0:", up) print("test1:", xp[0]**degree) u_exact = np.zeros(mesh.geometry.dim) u_exact[0] = xp[0]**degree assert np.allclose(up, u_exact)
def perform_test(points, cells): domain = ufl.Mesh(ufl.VectorElement("Lagrange", "tetrahedron", 1)) mesh = create_mesh(MPI.COMM_WORLD, cells, points, domain) V = FunctionSpace(mesh, (space_type, order)) f = Function(V) output = [] for dof in range(len(f.vector[:])): f.vector[:] = np.zeros(len(f.vector[:])) f.vector[dof] = 1 points = np.array([[1 / 3, 1 / 3, 1 / 3], [1 / 3, 1 / 3, 1 / 3]]) cells = np.array([0, 1]) result = f.eval(points, cells) normal = np.array([1., 1., 1.]) output.append(result.dot(normal)) return output
def perform_test(points, cells): mesh = Mesh(MPI.COMM_WORLD, CellType.tetrahedron, points, np.array(cells), []) V = FunctionSpace(mesh, (space_type, order)) f = Function(V) output = [] for dof in range(len(f.vector[:])): f.vector[:] = np.zeros(len(f.vector[:])) f.vector[dof] = 1 points = np.array([[1 / 3, 1 / 3, 1 / 3], [1 / 3, 1 / 3, 1 / 3]]) cells = np.array([0, 1]) result = f.eval(points, cells) normal = np.array([1., 1., 1.]) output.append(result.dot(normal)) return output
def perform_test(points, cells): mesh = cpp.mesh.Mesh(MPI.comm_world, CellType.tetrahedron, points, np.array(cells), [], cpp.mesh.GhostMode.none) mesh.geometry.coord_mapping = fem.create_coordinate_map(mesh) V = FunctionSpace(mesh, (space_type, order)) f = Function(V) output = [] for dof in range(len(f.vector[:])): f.vector[:] = np.zeros(len(f.vector[:])) f.vector[dof] = 1 points = np.array([[1 / 3, 1 / 3, 1 / 3], [1 / 3, 1 / 3, 1 / 3]]) cells = np.array([0, 1]) result = f.eval(points, cells) normal = np.array([1., 1., 1.]) output.append(result.dot(normal)) return output
def test_tetrahedron_evaluation(space_type, space_order): domain = ufl.Mesh(ufl.VectorElement("Lagrange", "tetrahedron", 1)) temp_points = np.array([[-1., 0., -1.], [0., 0., 0.], [1., 0., 1.], [0., 1., 0.], [0., 0., 1.]]) for repeat in range(10): order = [i for i, j in enumerate(temp_points)] shuffle(order) points = np.zeros(temp_points.shape) for i, j in enumerate(order): points[j] = temp_points[i] cells = [] for cell in [[0, 1, 3, 4], [1, 2, 3, 4]]: # Randomly number the cell cell_order = list(range(4)) shuffle(cell_order) cells.append([order[cell[i]] for i in cell_order]) mesh = create_mesh(MPI.COMM_WORLD, cells, points, domain) V = FunctionSpace(mesh, (space_type, space_order)) dofs = [i for i in V.dofmap.cell_dofs(0) if i in V.dofmap.cell_dofs(1)] N = 6 eval_points = np.array([[0., i / N, j / N] for i in range(N + 1) for j in range(N + 1 - i)]) for d in dofs: v = Function(V) v.vector[:] = [ 1 if i == d else 0 for i in range(v.vector.local_size) ] values0 = v.eval(eval_points, [0 for i in eval_points]) values1 = v.eval(eval_points, [1 for i in eval_points]) if len(eval_points) == 1: values0 = [values0] values1 = [values1] if space_type in ["RT", "BDM"]: # Hdiv for i, j in zip(values0, values1): assert np.isclose(i[0], j[0]) elif space_type in ["N1curl", "N2curl"]: # Hcurl for i, j in zip(values0, values1): assert np.allclose(i[1:], j[1:]) else: assert np.allclose(values0, values1)
def test_eval(R, V, W, Q, mesh): u0 = Function(R) u1 = Function(V) u2 = Function(W) u3 = Function(Q) def e1(x): return x[0] + x[1] + x[2] def e2(x): values = np.empty((3, x.shape[1])) values[0] = x[0] + x[1] + x[2] values[1] = x[0] - x[1] - x[2] values[2] = x[0] + x[1] + x[2] return values def e3(x): values = np.empty((9, x.shape[1])) values[0] = x[0] + x[1] + x[2] values[1] = x[0] - x[1] - x[2] values[2] = x[0] + x[1] + x[2] values[3] = x[0] values[4] = x[1] values[5] = x[2] values[6] = -x[0] values[7] = -x[1] values[8] = -x[2] return values u0.vector.set(1.0) u1.interpolate(e1) u2.interpolate(e2) u3.interpolate(e3) x0 = (mesh.geometry.x(0) + mesh.geometry.x(1)) / 2.0 tree = geometry.BoundingBoxTree(mesh, mesh.geometry.dim) cells = geometry.compute_first_entity_collision(tree, mesh, x0) assert np.allclose(u3.eval(x0, cells)[:3], u2.eval(x0, cells), rtol=1e-15, atol=1e-15) with pytest.raises(ValueError): u0.eval([0, 0, 0, 0], 0) with pytest.raises(ValueError): u0.eval([0, 0], 0)
k) fecoda.main.post_update(expr_compiled, intern_var0, intern_var1, w0, w1) fecoda.main.copyout_state(w0, w1, intern_var0, intern_var1) force.value += df.value bb_tree = BoundingBoxTree(mesh, 3) p = numpy.array([0.0, 0.0, 0.3], dtype=numpy.float64) cell_candidates = compute_collisions_point(bb_tree, p) cell = select_colliding_cells(mesh, cell_candidates, p, 1) interpolate(ufl.sym(ufl.grad(w1["displ"])), strain) if len(cell) > 0: value = strain.eval(p, cell) value = value[-1] else: value = None values = comm.gather(value, root=0) if rank == 0: value = [x for x in values if x is not None][0] compl = value * -1.0e+6 / args.sigma log["compl"].append(compl) log["times"].append(float(t.value) - tp - fecoda.mps.t_begin) # Flush log file with open(f"{filename}.log", "w") as file: json.dump(log, file)
def test_hexahedron_evaluation(space_type, space_order): if space_type == "NCF" and space_order >= 3: print("Eval in this space not supported yet") return if space_type == "NCE" and space_order >= 2: print("Eval in this space not supported yet") return domain = ufl.Mesh(ufl.VectorElement("Lagrange", "hexahedron", 1)) temp_points = np.array([[-1., 0., -1.], [0., 0., 0.], [1., 0., 1.], [-1., 1., 1.], [0., 1., 0.], [1., 1., 1.], [-1., 0., 0.], [0., 0., 1.], [1., 0., 2.], [-1., 1., 2.], [0., 1., 1.], [1., 1., 2.]]) for repeat in range(10): order = [i for i, j in enumerate(temp_points)] shuffle(order) points = np.zeros(temp_points.shape) for i, j in enumerate(order): points[j] = temp_points[i] connections = { 0: [1, 2, 4], 1: [0, 3, 5], 2: [0, 3, 6], 3: [1, 2, 7], 4: [0, 5, 6], 5: [1, 4, 7], 6: [2, 4, 7], 7: [3, 5, 6] } cells = [] for cell in [[0, 1, 3, 4, 6, 7, 9, 10], [1, 2, 4, 5, 7, 8, 10, 11]]: # Randomly number the cell start = choice(range(8)) cell_order = [start] for i in range(3): diff = choice([ i for i in connections[start] if i not in cell_order ]) - cell_order[0] cell_order += [c + diff for c in cell_order] cells.append([order[cell[i]] for i in cell_order]) mesh = create_mesh(MPI.COMM_WORLD, cells, points, domain) V = FunctionSpace(mesh, (space_type, space_order)) dofs = [i for i in V.dofmap.cell_dofs(0) if i in V.dofmap.cell_dofs(1)] N = 6 eval_points = np.array([[0., i / N, j / N] for i in range(N + 1) for j in range(N + 1)]) for d in dofs: v = Function(V) v.vector[:] = [1 if i == d else 0 for i in range(V.dim)] values0 = v.eval(eval_points, [0 for i in eval_points]) values1 = v.eval(eval_points, [1 for i in eval_points]) if len(eval_points) == 1: values0 = [values0] values1 = [values1] if space_type == "NCF": # Hdiv for i, j in zip(values0, values1): assert np.isclose(i[0], j[0]) elif space_type == "NCE": # Hcurl for i, j in zip(values0, values1): assert np.allclose(i[1:], j[1:]) else: assert np.allclose(values0, values1)