def runTest(self): # Mesh.remove_elements m = MeshTri() m.refine() M = m.remove_elements(np.array([0])) self.assertEqual(M.t.shape[1], 7) # Mesh.define_boundary m.define_boundary('foo', lambda x: x[0] == 0.) self.assertEqual(m.boundaries['foo'].size, 2) # Mesh.define_boundary (internal) m.define_boundary('bar', lambda x: x[0] == 1. / 2, boundaries_only=False) self.assertEqual(m.boundaries['bar'].size, 2) # Mesh.scale, Mesh.translate m = MeshHex() m.scale(0.5) m.translate((0.5, 0.5, 0.5)) self.assertGreater(np.min(m.p), 0.4999) # Mesh3D.facets_satisfying self.assertEqual(len(m.facets_satisfying(lambda x: x[0] == 0.5)), 1)
def runTest(self): mesh = MeshTri() mesh.refine(5) basis = InteriorBasis(mesh, ElementTriP1()) def fun(x, y): return x**2 + y**2 x = L2_projection(fun, basis) y = fun(*mesh.p) normest = np.linalg.norm(x - y) self.assertTrue(normest < 0.011, msg="|x-y| = {}".format(normest))
def runTest(self): """Solve Stokes problem, try splitting and other small things.""" m = MeshTri() m.refine() m.define_boundary('centreline', lambda x: x[0] == .5, boundaries_only=False) m.refine(3) e = ElementVectorH1(ElementTriP2()) * ElementTriP1() m.define_boundary('up', lambda x: x[1] == 1.) m.define_boundary('rest', lambda x: x[1] != 1.) basis = InteriorBasis(m, e) self.assertEqual( basis.get_dofs(m.boundaries['centreline']).all().size, (2 + 1) * (2**(1 + 3) + 1) + 2 * 2**(1 + 3)) self.assertEqual(basis.find_dofs()['centreline'].all().size, (2 + 1) * (2**(1 + 3) + 1) + 2 * 2**(1 + 3)) @BilinearForm def bilinf(u, p, v, q, w): from skfem.helpers import grad, ddot, div return (ddot(grad(u), grad(v)) - div(u) * q - div(v) * p - 1e-2 * p * q) S = asm(bilinf, basis) D = basis.find_dofs(skip=['u^2']) x = basis.zeros() x[D['up'].all('u^1^1')] = .1 x = solve(*condense(S, basis.zeros(), x=x, D=D)) (u, u_basis), (p, p_basis) = basis.split(x) self.assertEqual(len(u), m.p.shape[1] * 2 + m.facets.shape[1] * 2) self.assertEqual(len(p), m.p.shape[1]) self.assertTrue(np.sum(p - x[basis.nodal_dofs[2]]) < 1e-8) U, P = basis.interpolate(x) self.assertTrue(isinstance(U.value, np.ndarray)) self.assertTrue(isinstance(P.value, np.ndarray)) self.assertTrue((basis.doflocs[:, D['up'].all()][1] == 1.).all())
class ConvergenceRaviartThomas(unittest.TestCase): rateL2 = 1.0 rateHdiv = 1.0 eps = 0.1 Hdivbound = 0.04 L2bound = 0.01 def runTest(self): @BilinearForm def bilinf_A(sigma, tau, w): from skfem.models.helpers import dot return dot(sigma, tau) @BilinearForm def bilinf_B(sigma, v, w): return sigma.df * v @LinearForm def load(v, w): x = w.x if x.shape[0] == 1: return (np.sin(np.pi * x[0]) * (np.pi**2) * v) elif x.shape[0] == 2: return (np.sin(np.pi * x[0]) * np.sin(np.pi * x[1]) * (2.0 * np.pi**2) * v) elif x.shape[0] == 3: return (np.sin(np.pi * x[0]) * np.sin(np.pi * x[1]) * np.sin(np.pi * x[2]) * (3.0 * np.pi**2) * v) else: raise Exception("The dimension not supported") m = self.mesh Nitrs = 3 L2s = np.zeros(Nitrs) Hdivs = np.zeros(Nitrs) hs = np.zeros(Nitrs) for itr in range(Nitrs): ib1, ib2 = self.create_basis(m) A = asm(bilinf_A, ib1) B = asm(bilinf_B, ib1, ib2) b = np.concatenate((np.zeros(A.shape[0]), -asm(load, ib2))) from scipy.sparse import bmat K = bmat([[A, B.T], [B, None]]).tocsr() x = solve(K, b) # calculate error sigma, u = np.split(x, [A.shape[0]]) L2s[itr] = self.compute_L2(m, ib2, u) Hdivs[itr] = self.compute_Hdiv(m, ib1, sigma) hs[itr] = m.param() m.refine() rateL2 = np.polyfit(np.log(hs), np.log(L2s), 1)[0] rateHdiv = np.polyfit(np.log(hs), np.log(Hdivs), 1)[0] self.assertLess(np.abs(rateL2 - self.rateL2), self.eps, msg='observed L2 rate: {}'.format(rateL2)) self.assertLess(np.abs(rateHdiv - self.rateHdiv), self.eps, msg='observed Hdiv rate: {}'.format(rateHdiv)) self.assertLess(Hdivs[-1], self.Hdivbound) self.assertLess(L2s[-1], self.L2bound) def compute_L2(self, m, basis, U): uh, *_ = basis.interpolate(U) dx = basis.dx x = basis.global_coordinates() def u(y): if y.shape[0] == 1: return np.sin(np.pi * y[0]) elif y.shape[0] == 2: return (np.sin(np.pi * y[0]) * np.sin(np.pi * y[1])) return (np.sin(np.pi * y[0]) * np.sin(np.pi * y[1]) * np.sin(np.pi * y[2])) return np.sqrt(np.sum(np.sum((uh - u(x.f))**2 * dx, axis=1))) def compute_Hdiv(self, m, basis, U): uh, duh, *_ = basis.interpolate(U) dx = basis.dx x = basis.global_coordinates() def divu(y): if y.shape[0] == 1: return np.pi * np.cos(np.pi * y[0]) elif y.shape[0] == 2: return (np.pi * np.cos(np.pi * y[0]) * np.sin(np.pi * y[1]) + np.pi * np.sin(np.pi * y[0]) * np.cos(np.pi * y[1])) return np.pi * (np.cos(np.pi * y[0]) * np.sin(np.pi * y[1]) * np.sin(np.pi * y[2]) + np.sin(np.pi * y[0]) * np.cos(np.pi * y[1]) * np.sin(np.pi * y[2]) + np.sin(np.pi * y[0]) * np.sin(np.pi * y[1]) * np.cos(np.pi * y[2])) divuh = sum(uh) return np.sqrt(np.sum(np.sum(((divuh - divu(x.f))**2) * dx, axis=1))) def create_basis(self, m): e = ElementTriRT0() e0 = ElementTriP0() return (InteriorBasis(m, e, intorder=2), InteriorBasis(m, e0, intorder=2)) def setUp(self): self.mesh = MeshTri() self.mesh.refine(4)