Exemplo n.º 1
0
    def __init__(self, mesh, FuncSpace_dict, beta_map=Constant(1e-6), ds=ds):
        """
        Instantiate FormsPDEMap

        Parameters
        ----------
        mesh: dolfin.Mesh
            Dolfin Mesh
        FuncSpace_dict: dict
            Dictionary containing the function space definitions. Following keys are required:
                - FuncSpace_local: function space for local variable
                - FuncSpace_lambda: function space for Lagrange multiplier
                - FuncSpace_bar: function space for control variable
        beta_map: dolfin.Constant, optional
            Penalty/Regularizatio term to establish coupling between local unknown and control.
            Defaults to Constant(1e-6)
        ds: dolfin.Measure, optional
            ds Measure of mesh
        """

        self.W = FuncSpace_dict["FuncSpace_local"]
        self.T = FuncSpace_dict["FuncSpace_lambda"]
        self.Wbar = FuncSpace_dict["FuncSpace_bar"]

        self.n = FacetNormal(mesh)
        self.beta_map = beta_map
        self.ds = ds
        self.gdim = mesh.geometry().dim()
Exemplo n.º 2
0
    def solve(self, dt):
        self.u = Function(self.V0)
        self.w = TestFunction(self.V0)
        self.du = TrialFunction(self.V0)

        x = SpatialCoordinate(self.mesh0)

        L = inner( self.S(), self.eps(self.w) )*dx(degree=4)\
        - inner( self.b, self.w )*dx(degree=4)\
        - inner( self.h, self.w )*ds(degree=4)\
        + inner( 1e-6*self.u, self.w )*ds(degree=4)\
        - inner( min_value(x[2]+self.ut[2]+self.u[2], 0) * Constant((0,0,-1.0)), self.w )*ds(degree=4)

        a = derivative(L, self.u, self.du)

        problem = NonlinearVariationalProblem(L, self.u, bcs=[], J=a)
        solver = NonlinearVariationalSolver(problem)

        solver.solve()

        self.ut.vector()[:] = self.ut.vector()[:] + self.u.vector()[:]

        ALE.move(self.mesh, Function(self.V, self.u.vector()))

        self.v.vector()[:] = self.u.vector()[:] / dt
        self.n = FacetNormal(self.mesh)
Exemplo n.º 3
0
    def create_coupling_neumann_boundary_condition(self,
                                                   test_functions,
                                                   function_space=None,
                                                   boundary_marker=None):
        """Creates the coupling Neumann boundary conditions using
        create_coupling_boundary_condition() method.

        :return: expression in form of integral: g*v*ds. (see e.g. p. 83ff
         Langtangen, Hans Petter, and Anders Logg. "Solving PDEs in Python The
         FEniCS Tutorial Volume I." (2016).)
        """
        if not function_space:
            self._function_space = test_functions.function_space()
        else:
            self._function_space = function_space
        self._create_coupling_boundary_condition()
        if not boundary_marker:  # there is only 1 Neumann-BC which is at the coupling boundary -> integration over whole boundary
            if self._coupling_bc_expression.is_scalar_valued():
                return test_functions * self._coupling_bc_expression * dolfin.ds  # this term has to be added to weak form to add a Neumann BC (see e.g. p. 83ff Langtangen, Hans Petter, and Anders Logg. "Solving PDEs in Python The FEniCS Tutorial Volume I." (2016).)
            elif self._coupling_bc_expression.is_vector_valued():
                n = FacetNormal(self._mesh_fenics)
                return -test_functions * dot(
                    n, self._coupling_bc_expression) * dolfin.ds
            else:
                raise Exception("invalid!")
        else:  # For multiple Neumann BCs integration should only be performed over the respective domain.
            # TODO: fix the problem here
            raise Exception("Boundary markers are not implemented yet")
            return dot(self._coupling_bc_expression,
                       test_functions) * self.dss(boundary_marker)
Exemplo n.º 4
0
    def __init__(self, parameters, domain):
        rho = Constant(parameters["density [kg/m3]"])
        mu = Constant(parameters["viscosity [Pa*s]"])
        dt = Constant(parameters["dt [s]"])
        u, u_1, u_k, vu = domain.u, domain.u_1, domain.u_k, domain.vu
        p_1 = domain.p_1

        n = FacetNormal(domain.mesh)
        acceleration = rho*inner((u-u_1)/dt, vu) * dx
        convection = dot(div(rho*outer(u_k, u)), vu) * dx
        convection = rho*dot(dot(u_k, nabla_grad(u)), vu) * dx
        pressure = (inner(p_1, div(vu))*dx - dot(p_1*n, vu)*ds)
        diffusion = (-inner(mu * (grad(u) + grad(u).T), grad(vu))*dx)  # good
        # diffusion = (-inner(mu * (grad(u) + grad(u).T), grad(vu))*dx
        #               + dot(mu * (grad(u) + grad(u).T)*n, vu)*ds)  # very slow!

        # F_impl = acceleration + convection + pressure + diffusion

        # dot(u_1, nabla_grad(u_1)) works
        # dot(u, nabla_grad(u_1)) does not change!
        u_mid = (u + u_1) / 2.0
        F_impl = rho*dot((u - u_1) / dt, vu)*dx \
            + rho*dot(dot(u_1, nabla_grad(u_1)), vu)*dx \
            + inner(sigma(u_mid, p_1, mu), epsilon(vu))*dx \
            + dot(p_1*n, vu)*ds - dot(mu*nabla_grad(u_mid)*n, vu)*ds

        self.a, self.L = lhs(F_impl), rhs(F_impl)
        self.domain = domain
        self.A = assemble(self.a)
        [bc.apply(self.A) for bc in domain.bcu]
        return
    def __init__(self, domain):
        rho, mu, dt, g = domain.rho, domain.mu, domain.dt, domain.g
        u, u_1, vu = domain.u, domain.u_1, domain.vu
        p_1 = domain.p_1

        n = FacetNormal(domain.mesh)

        acceleration = rho * inner((u - u_1) / dt, vu) * dx
        pressure = inner(p_1, div(vu)) * dx - dot(p_1 * n, vu) * ds
        body_force = dot(g*rho, vu)*dx \
            + dot(Constant((0.0, 0.0)), vu) * ds
        # diffusion = (-inner(mu * (grad(u_1) + grad(u_1).T), grad(vu))*dx
        #               + dot(mu * (grad(u_1) + grad(u_1).T)*n, vu)*ds)  # just fine
        # diffusion = (-inner(mu * (grad(u) + grad(u).T), grad(vu))*dx)  # just fine
        # just fine, but horribly slow in combination with ???  -> not reproducable
        diffusion = (-inner(mu * (grad(u) + grad(u).T), grad(vu)) * dx +
                     dot(mu * (grad(u) + grad(u).T) * n, vu) * ds)
        # convection = rho*dot(dot(u, nabla_grad(u_1)), vu) * dx  # no vortices
        convection = rho * dot(dot(u_1, nabla_grad(u)), vu) * dx
        # stabilization = -gamma*psi_p*p_1
        # convection = dot(div(rho * outer(u_1, u_1)), vu) * dx  # not stable!
        # convection = rho * dot(dot(u_1, nabla_grad(u_1)), vu) * dx  # just fine
        F_impl = -acceleration - convection + diffusion + pressure + body_force

        self.a, self.L = lhs(F_impl), rhs(F_impl)
        self.domain = domain
        self.A = assemble(self.a)
        [bc.apply(self.A) for bc in domain.bcu]
        return
Exemplo n.º 6
0
            def _rhs(self, degree, y):
                base_potential = Expression(f'''
                    0.25 / ({np.pi * self.BASE_CONDUCTIVITY})
                    / sqrt((x[0])*(x[0])
                           + (x[1] - {y})*(x[1] - {y})
                           + (x[2])*(x[2]))
                    ''',
                                            degree=degree,
                                            domain=self._mesh)
                n = FacetNormal(self._mesh)
                return -sum(
                    (inner((Constant(c - self.BASE_CONDUCTIVITY) *
                            grad(base_potential)), grad(self._v)) * self._dx(x)
                     for x, c in self.CONDUCTIVITY.items()
                     if c != self.BASE_CONDUCTIVITY),
                    # # Eq. 20 at Piastra et al 2018
                    # sum((Constant(self.BASE_CONDUCTIVITY)
                    #      * inner(n, grad(self._base_potential))
                    #      * self._v
                    #      * self._ds(s))
                    #      for s in self.SURFACE_CONDUCTIVITY)

                    # Eq. 19 at Piastra et al 2018
                    sum((Constant(c) * inner(n, grad(base_potential)) *
                         self._v * self._ds(s))
                        for s, c in self.SURFACE_CONDUCTIVITY.items()))
Exemplo n.º 7
0
 def update_multimesh(self, step):
     move_norm = []
     hmins = []
     move_max = []
     for i in range(1, self.N):
         s_move = self.deformation[i - 1].copy(True)
         s_move.vector()[:] *= step
         # Approximate geodesic distance
         dDeform = Measure("ds", subdomain_data=self.mfs[i])
         n_i = FacetNormal(self.multimesh.part(i))
         geo_dist_i = inner(s_move, s_move)*\
                      dDeform(self.move_dict[i]["Deform"])
         move_norm.append(assemble(geo_dist_i))
         # move_max.append(project(sqrt(s_move[0]**2 + s_move[1]**2),
         #                         FunctionSpace(self.multimesh.part(i),"CG",1)
         #                         ).vector().max())
         # hmins.append(self.multimesh.part(i).hmin())
         ALE.move(self.multimesh.part(i), s_move)
     # Compute L2 norm of movement
     self.move_norm = sqrt(sum(move_norm))
     # self.move_max = max(move_max)
     # print(hmins, move_max)
     self.multimesh.build()
     for key in self.cover_points.keys():
         self.multimesh.auto_cover(key, self.cover_points[key])
Exemplo n.º 8
0
    def facet_normal(self):
        """
        Returns symbolic outward unit normal to the boundary facets.

        :returns: unit normal vector
        :rtype: :py:class:`ufl.geometry.FacetNormal`
        """
        return FacetNormal(self._mesh)
Exemplo n.º 9
0
    def __init__(self, mesh, FuncSpace_dict, beta_map=Constant(1E-6), ds=ds):
        self.W = FuncSpace_dict['FuncSpace_local']
        self.T = FuncSpace_dict['FuncSpace_lambda']
        self.Wbar = FuncSpace_dict['FuncSpace_bar']

        self.n = FacetNormal(mesh)
        self.beta_map = beta_map
        self.ds = ds
        self.gdim = mesh.geometry().dim()
Exemplo n.º 10
0
 def __init__(self, mesh, FuncSpaces_L, FuncSpaces_G, alpha, beta_stab=Constant(0.0), ds=ds):
     self.mixedL = FuncSpaces_L
     self.mixedG = FuncSpaces_G
     self.n = FacetNormal(mesh)
     self.beta_stab = beta_stab
     self.alpha = alpha
     self.he = CellDiameter(mesh)
     self.ds = ds
     self.gdim = mesh.geometry().dim()
Exemplo n.º 11
0
def fit(x0, y0, mesh, Eps, degree=1, verbose=False, solver='spsolve'):
    V = FunctionSpace(mesh, 'CG', degree)
    u = TrialFunction(V)
    v = TestFunction(V)

    n = FacetNormal(mesh)

    dim = mesh.geometry().dim()

    A = [
        _assemble_eigen(+Constant(Eps[i, j]) * u.dx(i) * v.dx(j) * dx
                        # pylint: disable=unsubscriptable-object
                        - Constant(Eps[i, j]) * u.dx(i) * n[j] * v *
                        ds).sparray() for i in range(dim) for j in range(dim)
    ]

    E = _build_eval_matrix(V, x0)

    M = sparse.vstack(A + [E])
    b = numpy.concatenate([numpy.zeros(sum(a.shape[0] for a in A)), y0])

    if solver == 'spsolve':
        MTM = M.T.dot(M)
        x = sparse.linalg.spsolve(MTM, M.T.dot(b))
    elif solver == 'lsqr':
        x, istop, *_ = sparse.linalg.lsqr(
            M,
            b,
            show=verbose,
            atol=1.0e-10,
            btol=1.0e-10,
        )
        assert istop == 2, \
            'sparse.linalg.lsqr not successful (error code {})'.format(istop)
    elif solver == 'lsmr':
        x, istop, *_ = sparse.linalg.lsmr(
            M,
            b,
            show=verbose,
            atol=1.0e-10,
            btol=1.0e-10,
            # min(M.shape) is the default
            maxiter=max(min(M.shape), 10000))
        assert istop == 2, \
            'sparse.linalg.lsmr not successful (error code {})'.format(istop)
    else:
        assert solver == 'gmres', 'Unknown solver \'{}\'.'.format(solver)
        A = sparse.linalg.LinearOperator((M.shape[1], M.shape[1]),
                                         matvec=lambda x: M.T.dot(M.dot(x)))
        x, info = sparse.linalg.gmres(A, M.T.dot(b), tol=1.0e-12)
        assert info == 0, \
            'sparse.linalg.gmres not successful (error code {})'.format(info)

    u = Function(V)
    u.vector().set_local(x)
    return u
Exemplo n.º 12
0
def navier_stokes_IPCS(mesh, dt, parameter):
    """
    fenics code: weak form of the problem.
    """
    mu, rho, nu = parameter
    V = VectorFunctionSpace(mesh, 'P', 2)
    Q = FunctionSpace(mesh, 'P', 1)

    bc0 = DirichletBC(V, Constant((0, 0)), cylinderwall)
    bc1 = DirichletBC(V, Constant((0, 0)), topandbottom)
    bc2 = DirichletBC(V, U0, inlet)
    bc3 = DirichletBC(Q, Constant(1), outlet)
    bcs = [bc0, bc1, bc2, bc3]

    # ds is needed to compute drag and lift. Not used here.
    ASD1 = AutoSubDomain(topandbottom)
    ASD2 = AutoSubDomain(cylinderwall)
    mf = MeshFunction("size_t", mesh, 1)
    mf.set_all(0)
    ASD1.mark(mf, 1)
    ASD2.mark(mf, 2)
    ds_ = ds(subdomain_data=mf, domain=mesh)

    vu, vp = TestFunction(V), TestFunction(Q)  # for integration
    u_, p_ = Function(V), Function(Q)  # for the solution
    u_1, p_1 = Function(V), Function(Q)  # for the prev. solution
    u, p = TrialFunction(V), TrialFunction(Q)  # unknown!
    bcu = [bcs[0], bcs[1], bcs[2]]
    bcp = [bcs[3]]

    n = FacetNormal(mesh)
    u_mid = (u + u_1) / 2.0
    F1 = rho*dot((u - u_1) / dt, vu)*dx \
        + rho*dot(dot(u_1, nabla_grad(u_1)), vu)*dx \
        + inner(sigma(u_mid, p_1, mu), epsilon(vu))*dx \
        + dot(p_1*n, vu)*ds - dot(mu*nabla_grad(u_mid)*n, vu)*ds
    a1 = lhs(F1)
    L1 = rhs(F1)
    # Define variational problem for step 2
    a2 = dot(nabla_grad(p), nabla_grad(vp)) * dx
    L2 = dot(nabla_grad(p_1), nabla_grad(vp)) * dx - (
        rho / dt) * div(u_) * vp * dx  # rho missing in FEniCS tutorial
    # Define variational problem for step 3
    a3 = dot(u, vu) * dx
    L3 = dot(u_, vu) * dx - dt * dot(nabla_grad(p_ - p_1), vu) * dx
    # Assemble matrices
    A1 = assemble(a1)
    A2 = assemble(a2)
    A3 = assemble(a3)
    # Apply boundary conditions to matrices
    [bc.apply(A1) for bc in bcu]
    [bc.apply(A2) for bc in bcp]
    return u_, p_, u_1, p_1, L1, A1, L2, A2, L3, A3, bcu, bcp
Exemplo n.º 13
0
 def assemble_lui_stiffness(self, g, f, mesh, robin_boundary):
     V = FunctionSpace(mesh, "Lagrange", self.p)
     u = TrialFunction(V)
     v = TestFunction(V)
     n = FacetNormal(mesh)
     robin = MeshFunction('size_t', mesh, mesh.topology().dim() - 1)
     robin_boundary.mark(robin, 1)
     ds = Measure('ds', subdomain_data=robin)
     a = inner(grad(u), grad(v)) * dx
     b = (1 - g) * (inner(grad(u), n)) * v * ds(1)
     c = f * u * v * ds(1)
     k = lhs(a + b - c)
     K = PETScMatrix()
     assemble(k, tensor=K)
     return K, V
 def __init__(self, domain):
     rho, mu, dt = domain.rho, domain.mu, domain.dt
     u, u_1, p_1, vu = domain.u, domain.u_1, domain.p_1, domain.vu
     n = FacetNormal(domain.mesh)
     acceleration = rho * inner((u - u_1) / dt, vu) * dx
     diffusion = (-inner(mu * (grad(u_1) + grad(u_1).T), grad(vu)) * dx +
                  dot(mu * (grad(u_1) + grad(u_1).T) * n, vu) * ds)
     pressure = inner(p_1, div(vu)) * dx - dot(p_1 * n, vu) * ds
     convection = rho * dot(dot(u_1, nabla_grad(u_1)), vu) * dx
     F_impl = -acceleration - convection + diffusion + pressure
     self.a, self.L = lhs(F_impl), rhs(F_impl)
     self.domain = domain
     self.A = assemble(self.a)
     [bc.apply(self.A) for bc in domain.bcu]
     return
Exemplo n.º 15
0
    def set_form(self, form):
        """
        This function is called by simulator.set_form to set up the equations
        for the electric field. This function will add the poisson
        equation to the variational form.

        Args:
            form: A FEniCS variational form.
        """
        # gather some variables
        v, d = self.simulator.v_phi, self.simulator.d_phi
        psi = self.simulator.psi
        sigma = interpolate(Constant(0), self.simulator.geometry.V)
        b = interpolate(Constant(0), self.simulator.geometry.V)

        # calculate sigma and b (used in boundary condition)
        for ion in self.simulator.ion_list:
            sigma += (1. / psi) * ion.z**2 * ion.D * ion.c
            b += ion.z * ion.D * ion.c

        # boundary condition
        g = inner(
            nabla_grad(b) / sigma, FacetNormal(self.simulator.geometry.mesh))

        # gather constants
        F = Constant(self.simulator.F)
        eps = Constant(self.simulator.epsilon)
        rho = Function(self.simulator.geometry.V)

        # calculate rho
        for ion in self.simulator.ion_list:
            rho += F * ion.z * ion.c_new

        self.rho = rho

        # update variational form
        form += (inner(nabla_grad(self.phi_new), nabla_grad(v)) +
                 self.dummy_new * v + self.phi_new * d - rho * v / eps) * dx
        form += g * v * ds

        v, d = self.simulator.v_phi_ps, self.simulator.d_phi_ps
        form += (inner(nabla_grad(self.phi_ps_new), nabla_grad(v)) +
                 self.phi_ps_new * d + v * self.dummy_ps_new) * dx

        return form
Exemplo n.º 16
0
        def __init__(self, V):
            self.sol = Expression(sympy.printing.ccode(solution),
                                  degree=MAX_DEGREE,
                                  t=0.0,
                                  cell=triangle)

            self.V = V
            u = TrialFunction(V)
            v = TestFunction(V)
            self.M = assemble(u * v * dx)

            n = FacetNormal(self.V.mesh())
            self.A = assemble(-inner(kappa * grad(u), grad(v /
                                                           (rho * cp))) * dx +
                              inner(kappa * grad(u), n) * v / (rho * cp) * ds)

            self.bcs = DirichletBC(self.V, self.sol, 'on_boundary')
            return
    def __init__(self, domain):
        rho, mu, dt = domain.rho, domain.mu, domain.dt
        u, u_1, vu = domain.u, domain.u_1, domain.vu
        p_1 = domain.p_1

        n = FacetNormal(domain.mesh)
        u_mid = (u + u_1) / 2.0
        F1 = rho * dot((u - u_1) / dt, vu) * dx \
            + rho * dot(dot(u_1, nabla_grad(u_1)), vu) * dx \
            + inner(sigma(u_mid, p_1, mu), epsilon(vu)) * dx \
            + dot(p_1 * n, vu) * ds - dot(mu * nabla_grad(u_mid) * n, vu) * ds
        a1 = lhs(F1)
        L1 = rhs(F1)
        A1 = assemble(a1)
        [bc.apply(A1) for bc in domain.bcu]

        self.a1, self.L1, self.A1 = a1, L1, A1
        self.domain = domain
        return
Exemplo n.º 18
0
 def generate_H1_deformation(self):
     self.deformation = []
     for i in range(1, self.N):
         S_i = VectorFunctionSpace(self.multimesh.part(i), "CG", 1)
         u_i, v_i = TrialFunction(S_i), TestFunction(S_i)
         d_free = Measure("ds",
                          domain=self.multimesh.part(i),
                          subdomain_data=self.mfs[i],
                          subdomain_id=self.move_dict[i]["Deform"])
         plot(-self.integrand_list[i - 1])
         plt.show()
         a_i = inner(u_i, v_i) * dx + 0.01 * inner(grad(u_i),
                                                   grad(v_i)) * dx
         n_i = FacetNormal(self.multimesh.part(i))
         l_i = inner(v_i, -self.integrand_list[i - 1]) * d_free
         s_i = Function(S_i)
         solve(a_i == l_i, s_i)
         plot(s_i)
         plt.show()
         self.deformation.append(s_i)
Exemplo n.º 19
0
 def __init__(self,
              mesh,
              FuncSpaces_L,
              FuncSpaces_G,
              alpha,
              h_d=[
                  Expression(('0.0', '0.0'), degree=3),
                  Expression(('0.0', '0.0'), degree=3)
              ],
              beta_stab=Constant(0.),
              ds=ds):
     self.mixedL = FuncSpaces_L
     self.mixedG = FuncSpaces_G
     self.n = FacetNormal(mesh)
     self.beta_stab = beta_stab
     self.alpha = alpha
     self.he = CellDiameter(mesh)
     self.h_d = h_d
     self.ds = ds
     self.gdim = mesh.geometry().dim()
Exemplo n.º 20
0
    def __init__(self, parameters, domain):
        rho = Constant(parameters["density [kg/m3]"])
        mu = Constant(parameters["viscosity [Pa*s]"])
        dt = Constant(parameters["dt [s]"])
        u, u_1, vu = domain.u, domain.u_1, domain.vu
        p_1 = domain.p_1

        n = FacetNormal(domain.mesh)
        u_mid = (u + u_1) / 2.0
        F1 = rho*dot((u - u_1) / dt, vu)*dx \
            + rho*dot(dot(u_1, nabla_grad(u_1)), vu)*dx \
            + inner(sigma(u_mid, p_1, mu), epsilon(vu))*dx \
            + dot(p_1*n, vu)*ds - dot(mu*nabla_grad(u_mid)*n, vu)*ds
        a1 = lhs(F1)
        L1 = rhs(F1)
        A1 = assemble(a1)
        [bc.apply(A1) for bc in domain.bcu]

        self.a1, self.L1, self.A1 = a1, L1, A1
        self.domain = domain
        return
Exemplo n.º 21
0
    def __init__(self, parameters, domain):
        rho = Constant(parameters["density [kg/m3]"])
        mu = Constant(parameters["viscosity [Pa*s]"])
        dt = Constant(parameters["dt [s]"])
        u, u_1, p_1, vu = domain.u, domain.u_1, domain.p_1, domain.vu

        n = FacetNormal(domain.mesh)
        acceleration = rho*inner((u-u_1)/dt, vu) * dx
        convection = dot(div(rho*outer(u_1, u)), vu) * dx
        diffusion = (-inner(mu * (grad(u_1) + grad(u_1).T), grad(vu))*dx
                     + dot(mu * (grad(u_1) + grad(u_1).T)*n, vu)*ds)
        pressure = inner(p_1, div(vu))*dx - dot(p_1*n, vu)*ds  # int. by parts
        # TODO: what is better?
        # convection = rho*dot(dot(u_1, nabla_grad(u_k)), vu) * dx
        # diffusion = (mu*inner(grad(u_1), grad(vu))*dx
        #              - mu*dot(nabla_grad(u_1)*n, vu)*ds)  # int. by parts
        F_impl = - acceleration - convection + diffusion + pressure
        self.a, self.L = lhs(F_impl), rhs(F_impl)
        self.domain = domain
        self.A = assemble(self.a)
        [bc.apply(self.A) for bc in domain.bcu]
        return
Exemplo n.º 22
0
 def adaptive(self, mesh, eigv, eigf):
     """Refine mesh based on residual errors."""
     fraction = 0.1
     C = FunctionSpace(mesh, "DG", 0)  # constants on triangles
     w = TestFunction(C)
     h = CellSize(mesh)
     n = FacetNormal(mesh)
     marker = CellFunction("bool", mesh)
     print len(marker)
     indicators = np.zeros(len(marker))
     for e, u in zip(eigv, eigf):
         errform = avg(h) * jump(grad(u), n) ** 2 * avg(w) * dS \
             + h * (inner(grad(u), n) - Constant(e) * u) ** 2 * w * ds
         if self.degree > 1:
             errform += h**2 * div(grad(u))**2 * w * dx
         indicators[:] += assemble(errform).array()  # errors for each cell
     print "Residual error: ", sqrt(sum(indicators) / len(eigv))
     cutoff = sorted(indicators,
                     reverse=True)[int(len(indicators) * fraction) - 1]
     marker.array()[:] = indicators > cutoff  # mark worst errors
     mesh = refine(mesh, marker)
     return mesh
Exemplo n.º 23
0
    def solve(self):
        """
        Solves the stokes equation with the current multimesh
        """
        (u, p) = TrialFunctions(self.VQ)
        (v, q) = TestFunctions(self.VQ)
        n = FacetNormal(self.multimesh)
        h = 2.0 * Circumradius(self.multimesh)
        alpha = Constant(6.0)

        tensor_jump = lambda u: outer(u("+"), n("+")) + outer(u("-"), n("-"))

        a_s = inner(grad(u), grad(v)) * dX
        a_IP = - inner(avg(grad(u)), tensor_jump(v))*dI\
               - inner(avg(grad(v)), tensor_jump(u))*dI\
               + alpha/avg(h) * inner(jump(u), jump(v))*dI
        a_O = inner(jump(grad(u)), jump(grad(v))) * dO

        b_s = -div(u) * q * dX - div(v) * p * dX
        b_IP = jump(u, n) * avg(q) * dI + jump(v, n) * avg(p) * dI
        l_s = inner(self.f, v) * dX

        s_C = h*h*inner(-div(grad(u)) + grad(p), -div(grad(v)) - grad(q))*dC\
              + h("+")*h("+")*inner(-div(grad(u("+"))) + grad(p("+")),
                                    -div(grad(v("+"))) + grad(q("+")))*dO
        l_C = h*h*inner(self.f, -div(grad(v)) - grad(q))*dC\
              + h("+")*h("+")*inner(self.f("+"),
                                    -div(grad(v("+"))) - grad(q("+")))*dO

        a = a_s + a_IP + a_O + b_s + b_IP + s_C
        l = l_s + l_C

        A = assemble_multimesh(a)
        L = assemble_multimesh(l)
        [bc.apply(A, L) for bc in self.bcs]
        self.VQ.lock_inactive_dofs(A, L)
        solve(A, self.w.vector(), L, "mumps")
        self.splitMMF()
    def __init__(self, domain):
        rho, mu, dt, g = domain.rho, domain.mu, domain.dt, domain.g
        u, u_1, p_1, vu = domain.u, domain.u_1, domain.p_1, domain.vu

        n = FacetNormal(domain.mesh)
        acceleration = rho * inner((u - u_1) / dt, vu) * dx
        diffusion = (-inner(mu * (grad(u_1) + grad(u_1).T), grad(vu)) * dx +
                     dot(mu * (grad(u_1) + grad(u_1).T) * n, vu) * ds)
        body_force = dot(g*rho, vu)*dx \
            + dot(Constant((0.0, 0.0)), vu) * ds
        # diffusion = (mu*inner(grad(u_1), grad(vu))*dx
        #              - mu*dot(nabla_grad(u_1)*n, vu)*ds)  # int. by parts
        pressure = inner(p_1, div(vu)) * dx - dot(p_1 * n,
                                                  vu) * ds  # int. by parts
        # TODO: what is better?
        # convection = dot(div(rho*outer(u_1, u_1)), vu) * dx  # not stable!
        convection = rho * dot(dot(u_1, nabla_grad(u_1)), vu) * dx
        F_impl = -acceleration - convection + diffusion + pressure + body_force
        self.a, self.L = lhs(F_impl), rhs(F_impl)
        self.domain = domain
        self.A = assemble(self.a)
        [bc.apply(self.A) for bc in domain.bcu]
        return
Exemplo n.º 25
0
    def before_first_compute(self, get):
        u = get("Velocity")
        V = u.function_space()

        spaces = SpacePool(V.mesh())
        degree = V.ufl_element().degree()

        if degree <= 1:
            Q = spaces.get_grad_space(V, shape=(spaces.d, ))
        else:
            if degree > 2:
                cbc_warning(
                    "Unable to handle higher order WSS space. Using CG1.")
            Q = spaces.get_space(1, 1)

        Q_boundary = spaces.get_space(Q.ufl_element().degree(),
                                      1,
                                      boundary=True)

        self.v = TestFunction(Q)
        self.tau = Function(Q, name="WSS_full")
        self.tau_boundary = Function(Q_boundary, name="WSS")

        local_dofmapping = mesh_to_boundarymesh_dofmap(spaces.BoundaryMesh, Q,
                                                       Q_boundary)
        self._keys = np.array(local_dofmapping.keys(), dtype=np.intc)
        self._values = np.array(local_dofmapping.values(), dtype=np.intc)
        self._temp_array = np.zeros(len(self._keys), dtype=np.float_)

        Mb = assemble(
            inner(TestFunction(Q_boundary), TrialFunction(Q_boundary)) * dx)
        self.solver = create_solver("gmres", "jacobi")
        self.solver.set_operator(Mb)

        self.b = Function(Q_boundary).vector()

        self._n = FacetNormal(V.mesh())
Exemplo n.º 26
0
def test_local_assembler_on_facet_integrals2():
    mesh = UnitSquareMesh(MPI.comm_world, 4, 4)
    Vu = VectorFunctionSpace(mesh, 'DG', 1)
    Vv = FunctionSpace(mesh, 'DGT', 1)
    u = TrialFunction(Vu)
    v = TestFunction(Vv)
    n = FacetNormal(mesh)

    # Define form
    a = dot(u, n) * v * ds
    for R in '+-':
        a += dot(u(R), n(R)) * v(R) * dS

    # Compile form. This is collective
    a = Form(a)

    # Get global cell 0. This will return a cell only on one of the
    # processes
    c = get_cell_at(mesh, 1 / 6, 1 / 12, 0)

    if c:
        A_e = assemble_local(a, c)
        A_correct = numpy.array([[0, 1 / 12, 1 / 24, 0, 0, 0],
                                 [0, 1 / 24, 1 / 12, 0, 0, 0],
                                 [-1 / 12, 0, -1 / 24, 1 / 12, 0, 1 / 24],
                                 [-1 / 24, 0, -1 / 12, 1 / 24, 0, 1 / 12],
                                 [0, 0, 0, -1 / 12, -1 / 24, 0],
                                 [0, 0, 0, -1 / 24, -1 / 12, 0]])
        error = ((A_e - A_correct)**2).sum()**0.5
        error = float(error)  # MPI.max does strange things to numpy.float64

    else:
        error = 0.0

    error = MPI.max(MPI.comm_world, float(error))
    assert error < 1e-16
Exemplo n.º 27
0
    def __init__(self, mesh0=UnitCubeMesh(8, 8, 8), params={}):
        parameters['form_compiler']['representation'] = 'uflacs'
        parameters['form_compiler']['optimize'] = True
        parameters['form_compiler']['quadrature_degree'] = 4

        self.mesh0 = Mesh(mesh0)
        self.mesh = Mesh(mesh0)

        if not 'C1' in params:
            params['C1'] = 100

        self.params = params

        self.b = Constant((0.0, 0.0, 0.0))
        self.h = Constant((0.0, 0.0, 0.0))

        self.C0 = FunctionSpace(self.mesh0, "Lagrange", 2)
        self.V0 = VectorFunctionSpace(self.mesh0, "Lagrange", 1)
        self.W0 = TensorFunctionSpace(self.mesh0, "Lagrange", 1)

        self.C = FunctionSpace(self.mesh, "Lagrange", 2)
        self.V = VectorFunctionSpace(self.mesh, "Lagrange", 1)
        self.W = TensorFunctionSpace(self.mesh, "Lagrange", 1)

        self.G = project(Identity(3), self.W0)

        self.ut = Function(self.V0)

        self.du = TestFunction(self.V0)
        self.w = TrialFunction(self.V0)

        self.n0 = FacetNormal(self.mesh0)

        self.v = Function(self.V)

        self.t = 0.0
Exemplo n.º 28
0
    def _setup_dg1_projection_2D(self, w, incompressibility_flux_type, D12,
                                 use_bcs):
        """
        Implement the projection where the result is BDM embeded in a DG1 function
        """
        sim = self.simulation
        k = 1
        gdim = 2
        mesh = w[0].function_space().mesh()
        V = VectorFunctionSpace(mesh, 'DG', k)
        W = FunctionSpace(mesh, 'DGT', k)
        n = FacetNormal(mesh)

        v1 = TestFunction(W)
        u = TrialFunction(V)

        # The same fluxes that are used in the incompressibility equation
        if incompressibility_flux_type == 'central':
            u_hat_dS = dolfin.avg(w)
        elif incompressibility_flux_type == 'upwind':
            w_nU = (dot(w, n) + abs(dot(w, n))) / 2.0
            switch = dolfin.conditional(dolfin.gt(w_nU('+'), 0.0), 1.0, 0.0)
            u_hat_dS = switch * w('+') + (1 - switch) * w('-')

        if D12 is not None:
            u_hat_dS += dolfin.Constant([D12, D12]) * dolfin.jump(w, n)

        # Equation 1 - flux through the sides
        a = L = 0
        for R in '+-':
            a += dot(u(R), n(R)) * v1(R) * dS
            L += dot(u_hat_dS, n(R)) * v1(R) * dS

        # Eq. 1 cont. - flux through external boundaries
        a += dot(u, n) * v1 * ds
        if use_bcs:
            for d in range(gdim):
                dirichlet_bcs = sim.data['dirichlet_bcs']['u%d' % d]
                neumann_bcs = sim.data['neumann_bcs'].get('u%d' % d, [])
                robin_bcs = sim.data['robin_bcs'].get('u%d' % d, [])
                outlet_bcs = sim.data['outlet_bcs']

                for dbc in dirichlet_bcs:
                    u_bc = dbc.func()
                    L += u_bc * n[d] * v1 * dbc.ds()

                for nbc in neumann_bcs + robin_bcs + outlet_bcs:
                    if nbc.enforce_zero_flux:
                        pass  # L += 0
                    else:
                        L += w[d] * n[d] * v1 * nbc.ds()

            for sbc in sim.data['slip_bcs'].get('u', []):
                pass  # L += 0
        else:
            L += dot(w, n) * v1 * ds

        # Equation 2 - internal shape   :   empty for DG1
        # Equation 3 - BDM Phi          :   empty for DG1

        return a, L, V
Exemplo n.º 29
0
    for k, cell in enumerate(cells):
        editor.add_cell(k, cell)
    editor.close()
    return mesh


mesh = UnitSquareMesh(200, 200)
# mesh = create_dolfin_mesh(*meshzoo.triangle(1500, corners=[[0, 0], [1, 0], [0, 1]]))


V = FunctionSpace(mesh, "CG", 1)

u = TrialFunction(V)
v = TestFunction(V)

n = FacetNormal(mesh)
# A = assemble(dot(grad(u), grad(v)) * dx - dot(n, grad(u)) * v * ds)
A = assemble(dot(grad(u), grad(v)) * dx - dot(n, grad(u)) * v * ds)
M = assemble(u * v * dx)

f = Expression("sin(pi * x[0]) * sin(pi * x[1])", element=V.ufl_element())
x = project(f, V)

Ax = A * x.vector()
Minv_Ax = Function(V).vector()
solve(M, Minv_Ax, Ax)
val = Ax.inner(Minv_Ax)

print(val)

Exemplo n.º 30
0
    def _setup_projection_nedelec(self, w, incompressibility_flux_type, D12,
                                  use_bcs, pdeg, gdim):
        """
        Implement the BDM-like projection using Nedelec elements in the test function
        """
        sim = self.simulation
        k = pdeg
        mesh = w[0].function_space().mesh()
        V = VectorFunctionSpace(mesh, 'DG', k)
        n = FacetNormal(mesh)

        # The mixed function space of the projection test functions
        e1 = FiniteElement('DGT', mesh.ufl_cell(), k)
        e2 = FiniteElement('N1curl', mesh.ufl_cell(), k - 1)
        em = MixedElement([e1, e2])
        W = FunctionSpace(mesh, em)
        v1, v2 = TestFunctions(W)
        u = TrialFunction(V)

        # The same fluxes that are used in the incompressibility equation
        if incompressibility_flux_type == 'central':
            u_hat_dS = dolfin.avg(w)
        elif incompressibility_flux_type == 'upwind':
            w_nU = (dot(w, n) + abs(dot(w, n))) / 2.0
            switch = dolfin.conditional(dolfin.gt(w_nU('+'), 0.0), 1.0, 0.0)
            u_hat_dS = switch * w('+') + (1 - switch) * w('-')

        if D12 is not None:
            u_hat_dS += dolfin.Constant([D12] * gdim) * dolfin.jump(w, n)

        # Equation 1 - flux through the sides
        a = L = 0
        for R in '+-':
            a += dot(u(R), n(R)) * v1(R) * dS
            L += dot(u_hat_dS, n(R)) * v1(R) * dS

        # Eq. 1 cont. - flux through external boundaries
        a += dot(u, n) * v1 * ds
        if use_bcs:
            for d in range(gdim):
                dirichlet_bcs = sim.data['dirichlet_bcs'].get('u%d' % d, [])
                neumann_bcs = sim.data['neumann_bcs'].get('u%d' % d, [])
                robin_bcs = sim.data['robin_bcs'].get('u%d' % d, [])
                outlet_bcs = sim.data['outlet_bcs']

                for dbc in dirichlet_bcs:
                    u_bc = dbc.func()
                    L += u_bc * n[d] * v1 * dbc.ds()

                for nbc in neumann_bcs + robin_bcs + outlet_bcs:
                    if nbc.enforce_zero_flux:
                        pass  # L += 0
                    else:
                        L += w[d] * n[d] * v1 * nbc.ds()

            for sbc in sim.data['slip_bcs'].get('u', []):
                pass  # L += 0
        else:
            L += dot(w, n) * v1 * ds

        # Equation 2 - internal shape using 'Nedelec 1st kind H(curl)' elements
        a += dot(u, v2) * dx
        L += dot(w, v2) * dx

        return a, L, V