def __init__(me, V, max_smooth_vectors=50):
        R = fenics.FunctionSpace(V.mesh(), 'R', 0)

        u_trial = fenics.TrialFunction(V)
        v_test = fenics.TestFunction(V)
        c_trial = fenics.TrialFunction(R)
        d_test = fenics.TestFunction(R)
        a11 = fenics.inner(fenics.grad(u_trial),
                           fenics.grad(v_test)) * fenics.dx
        a12 = c_trial * v_test * fenics.dx
        a21 = u_trial * d_test * fenics.dx
        A11 = convert_fenics_csr_matrix_to_scipy_csr_matrix(
            fenics.assemble(a11))
        A12 = convert_fenics_csr_matrix_to_scipy_csr_matrix(
            fenics.assemble(a12))
        A21 = convert_fenics_csr_matrix_to_scipy_csr_matrix(
            fenics.assemble(a21))
        me.A = sps.bmat([[A11, A12], [A21, None]]).tocsc()
        solve_A = spla.factorized(me.A)

        m = u_trial * v_test * fenics.dx
        me.M = convert_fenics_csr_matrix_to_scipy_csr_matrix(
            fenics.assemble(m)).tocsc()
        solve_M = spla.factorized(me.M)

        def solve_neumann(f_vec):
            fe_vec = np.concatenate([f_vec, np.array([0])])
            ue_vec = solve_A(fe_vec)
            u_vec = ue_vec[:-1]
            return u_vec

        me.solve_neumann_linop = spla.LinearOperator((V.dim(), V.dim()),
                                                     matvec=solve_neumann)
        me.solve_M_linop = spla.LinearOperator((V.dim(), V.dim()),
                                               matvec=solve_M)

        ee, UU = spla.eigsh(me.solve_neumann_linop,
                            k=max_smooth_vectors - 1,
                            M=me.solve_M_linop,
                            which='LM')

        me.U_smooth = np.zeros((V.dim(), max_smooth_vectors))
        const_fct = np.ones(V.dim())
        me.U_smooth[:, 0] = const_fct / np.sqrt(
            np.dot(const_fct, me.M * const_fct))
        me.U_smooth[:, 1:] = solve_M(UU[:, ::-1])

        me.k = 0
    def _assemble(self) -> Tuple[fenics.PETScMatrix, fenics.PETScMatrix]:
        """Construct matrices for generalized eigenvalue problem.

        Assemble the left and the right hand side of the eigenfunction
        equation into the corresponding matrices.

        Returns
        -------
        A : fenics.PETScMatrix
            Matrix corresponding to the form $a(u, v)$.
        B : fenics.PETScMatrix
            Matrix corresponding to the form $b(u, v)$.

        """
        V = self.vector_space

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

        a, b = self._construct_eigenproblem(u, v)

        A = fenics.PETScMatrix()
        B = fenics.PETScMatrix()

        fenics.assemble(a * fenics.dx, tensor=A)
        fenics.assemble(b * fenics.dx, tensor=B)

        return A, B
Esempio n. 3
0
    def __init__(self, K):
        # Variables
        x, y = sym.symbols('x[0], x[1]', real=True, positive=True)
        f = sym.Function('f')(x, y)

        grid = np.linspace(0, 1, K + 2)[1:-1]
        x_obs, y_obs = np.meshgrid(grid, grid)
        self.x_obs, self.y_obs = x_obs.reshape(K * K), y_obs.reshape(K * K)

        # --- THIS PART USED TO NOT BE PARALELLIZABLE --- #
        # Create mesh and define function space
        n_mesh = 80
        self.mesh = fen.UnitSquareMesh(n_mesh, n_mesh)
        self.f_space = fen.FunctionSpace(self.mesh, 'P', 2)

        # Define boundary condition
        # u_boundary = fen.Expression('x[0] + x[1]', degree=2)
        u_boundary = fen.Expression('0', degree=2)
        self.bound_cond = fen.DirichletBC(self.f_space, u_boundary,
                                          lambda x, on_boundary: on_boundary)

        # Define variational problem
        self.trial_f = fen.TrialFunction(self.f_space)
        self.test_f = fen.TestFunction(self.f_space)
        rhs = fen.Constant(50)

        self.lin_func = rhs * self.test_f * fen.dx
Esempio n. 4
0
 def generate_mesh(self, typ, order, resolution):
     self._mesh = mshr.generate_mesh(self._domain, resolution)
     self.input['mesh'] = self._mesh
     self._V = FEN.FunctionSpace(self._mesh, typ, order)
     self.input['V'] = self._V
     self._u = FEN.TrialFunction(self._V)
     self._v = FEN.TestFunction(self._V)
Esempio n. 5
0
def solver(f, u_D, bc_funs, ndim, length, nx, ny, nz=None, degree=1):
    """Fenics 求解器

    Args:
        f (Expression): [description]
        u_D (Expression): [description]
        bc_funs (List[Callable]): [description]
        ndim (int): [description]
        length (float): [description]
        nx (int): [description]
        ny (int): [description]
        nz (int, optional): [description]. Defaults to None.
        degree (int, optional): [description]. Defaults to 1.

    Returns:
        Function: 解 u
    """

    mesh = get_mesh(length, nx, ny, nz)
    V = fs.FunctionSpace(mesh, "P", degree)
    bcs = [fs.DirichletBC(V, u_D, bc) for bc in bc_funs]
    u = fs.TrialFunction(V)
    v = fs.TestFunction(V)
    FF = fs.dot(fs.grad(u), fs.grad(v)) * fs.dx - f * v * fs.dx
    a = fs.lhs(FF)
    L = fs.rhs(FF)
    u = fs.Function(V)
    fs.solve(a == L, u, bcs)
    return u
Esempio n. 6
0
    def eva(self, num):
        # construct basis functions, Set num points corresponding to num basis functions
        basPoints = np.linspace(0, 1, num)
        dx = basPoints[1] - basPoints[0]
        aa, bb, cc = -dx, 0.0, dx
        for x_p in basPoints:
            self.theta.append(
                fe.interpolate(
                    fe.Expression(
                        'x[0] < a || x[0] > c ? 0 : (x[0] >=a && x[0] <= b ? (x[0]-a)/(b-a) : 1-(x[0]-b)/(c-b))',
                        degree=2,
                        a=aa,
                        b=bb,
                        c=cc), self.Vc))
            aa, bb, cc = aa + dx, bb + dx, cc + dx

        u_trial, u_test = fe.TrialFunction(self.Vu), fe.TestFunction(self.Vu)
        left = fe.inner(self.al * fe.nabla_grad(u_trial),
                        fe.nabla_grad(u_test)) * fe.dx
        right = self.f * u_test * fe.dx

        def boundaryD(x, on_boundary):
            return on_boundary and fe.near(x[1], 1.0)

        for i in range(num):
            uH = fe.Function(self.Vu)
            bcD = fe.DirichletBC(self.Vu, self.theta[i], boundaryD)
            left_m, right_m = fe.assemble_system(left, right, bcD)
            fe.solve(left_m, uH.vector(), right_m)
            self.sol.append(uH)
Esempio n. 7
0
def vjp_assemble_impl(
    g: np.array,
    fenics_output_form: ufl.Form,
    fenics_inputs: List[FenicsVariable],
) -> Tuple[np.array]:
    """Computes the gradients of the output with respect to the inputs."""

    # Compute derivative form for the output with respect to each input
    fenics_grads_forms = []
    for fenics_input in fenics_inputs:
        # Need to construct direction (test function) first
        if isinstance(fenics_input, fenics.Function):
            V = fenics_input.function_space()
        elif isinstance(fenics_input, fenics.Constant):
            mesh = fenics_output_form.ufl_domain().ufl_cargo()
            V = fenics.FunctionSpace(mesh, "Real", 0)
        else:
            raise NotImplementedError

        dv = fenics.TestFunction(V)
        fenics_grad_form = fenics.derivative(fenics_output_form, fenics_input,
                                             dv)
        fenics_grads_forms.append(fenics_grad_form)

    # Assemble the derivative forms
    fenics_grads = [fenics.assemble(form) for form in fenics_grads_forms]

    # Convert FEniCS gradients to jax array representation
    jax_grads = (None if fg is None else np.asarray(g * fenics_to_numpy(fg))
                 for fg in fenics_grads)

    jax_grad_tuple = tuple(jax_grads)

    return jax_grad_tuple
Esempio n. 8
0
def fenics_solve(f):
    u = fa.Function(V, name="State")
    v = fn.TestFunction(V)
    F = (ufl.inner(ufl.grad(u), ufl.grad(v)) - f * v) * ufl.dx
    bcs = [fa.DirichletBC(V, 0.0, "on_boundary")]
    fa.solve(F == 0, u, bcs)
    return u
Esempio n. 9
0
 def solve_pde(self):
     u = fe.Function(self.function_space)
     v = fe.TestFunction(self.function_space)
     u_old = fe.project(self.u_0, self.function_space)
     # Todo: Average right hand side if we choose it non-constant
     flux = self.dt * fe.dot(
         self.composed_diff_coef *
         (fe.grad(u) + self.drift_function(u)), fe.grad(v)) * fe.dx
     bilin_part = u * v * fe.dx + flux
     funtional_part = self.rhs * v * self.dt * fe.dx + u_old * v * fe.dx
     full_form = bilin_part - funtional_part
     num_steps = int(self.T / self.dt) + 1
     bc = fe.DirichletBC(self.function_space, self.u_boundary,
                         MembraneSimulator.full_boundary)
     for n in range(num_steps):
         print("Step %d" % n)
         self.time += self.dt
         fe.solve(full_form == 0, u, bc)
         # fe.plot(u)
         # plt.show()
         # print(fe.errornorm(u_old, u))
         u_old.assign(u)
         self.file << (u, self.time)
     f = fe.plot(u)
     plt.rc('text', usetex=True)
     plt.colorbar(f, format='%.0e')
     plt.title(r'Macroscopic density profile of $u(x,t)$ at $t=1$')
     plt.xlabel(r'$x_1$')
     plt.ylabel(r'$x_2$')
     plt.show()
Esempio n. 10
0
    def __call__(self, mesh, V=None, Vc=None):

        boundaries, boundarymarkers, domainmarkers, dx, ds, V, Vc = SetupUnitMeshHelper(
            mesh, V, Vc)

        self._ds_markers = boundarymarkers
        self._dx_markers = domainmarkers

        self._dx = dx
        self._ds = ds
        self._boundaries = boundaries
        self._subdomains = self._boundaries

        u = df.TrialFunction(V)
        v = df.TestFunction(V)
        alpha = df.Function(Vc, name='conductivity')
        alpha.vector()[:] = 1

        def set_alpha(x):
            alpha.vector()[:] = x

        self._set_alpha = set_alpha
        a = alpha * df.inner(df.grad(u), df.grad(v)) * dx

        return a, set_alpha, alpha, V, Vc
Esempio n. 11
0
    def __setup_decrease_computation(self):
        """Initializes attributes and solver for the frobenius norm check.

		Returns
		-------
		None
		"""

        if not self.angle_change > 0:
            raise ConfigError('MeshQuality', 'angle_change',
                              'This parameter has to be positive.')

        options = [[['ksp_type', 'preonly'], ['pc_type', 'jacobi'],
                    ['pc_jacobi_type', 'diagonal'], ['ksp_rtol', 1e-16],
                    ['ksp_atol', 1e-20], ['ksp_max_it', 1000]]]
        self.ksp_frobenius = PETSc.KSP().create()
        _setup_petsc_options([self.ksp_frobenius], options)

        self.trial_dg0 = fenics.TrialFunction(self.form_handler.DG0)
        self.test_dg0 = fenics.TestFunction(self.form_handler.DG0)

        if not (self.angle_change == float('inf')):
            self.search_direction_container = fenics.Function(
                self.form_handler.deformation_space)

            self.a_frobenius = self.trial_dg0 * self.test_dg0 * self.dx
            self.L_frobenius = fenics.sqrt(
                fenics.inner(fenics.grad(self.search_direction_container),
                             fenics.grad(self.search_direction_container))
            ) * self.test_dg0 * self.dx
    def _make_variational_problem(V):
        """
        Formulate the variational problem a(u, v) = L(v).

        Parameters
        ----------
        V: FEniCS.FunctionSpace

        Returns
        -------
        a, L: FEniCS.Expression
            Variational forms.
        """
        # Define trial and test functions
        u = F.TrialFunction(V)
        v = F.TestFunction(V)

        # Collect Neumann conditions
        ds = F.Measure("ds", domain=mesh, subdomain_data=boundary_markers)
        integrals_N = []
        for i in boundary_conditions:
            if isinstance(boundary_conditions[i], dict):
                if "Neumann" in boundary_conditions[i]:
                    if boundary_conditions[i]["Neumann"] != 0:
                        g = boundary_conditions[i]["Neumann"]
                        integrals_N.append(g[0] * v * ds(i))

        # Define variational problem
        a = F.inner(u, v) * F.dx + (DT**2) * (C**2) * F.inner(
            F.grad(u), F.grad(v)) * F.dx
        L = ((DT**2) * f[0] + 2 * u_nm1 -
             u_nm2) * v * F.dx + (DT**2) * (C**2) * sum(integrals_N)
        return a, L
Esempio n. 13
0
def setup_vectorspace(mesh):
    """setup"""
    V = fe.VectorFunctionSpace(mesh, "CG", 1, dim=3)
    v = fe.TestFunction(V)
    u = fe.TrialFunction(V)
    m = fe.Function(V)
    Heff = fe.Function(V)
    return m, Heff, u, v, V
Esempio n. 14
0
    def compute_mesh_volume(self):

        one = fe.Constant(1)
        DG = fe.FunctionSpace(self.mesh, 'DG', 0)
        v = fe.TestFunction(DG)
        L = v * one * fe.dx
        b = fe.assemble(L)
        self.mesh_volume = b.get_local().sum()
Esempio n. 15
0
 def geneForwardMatrix(self, q_fun=fe.Constant(0.0), fR=fe.Constant(0.0), \
                       fI=fe.Constant(0.0)):
     if self.haveFunctionSpace == False:
         self.geneFunctionSpace()
         
     xx, yy, dPML, sig0_, p_ = self.domain.xx, self.domain.yy, self.domain.dPML,\
                               self.domain.sig0, self.domain.p
     # define the coefficents induced by PML
     sig1 = fe.Expression('x[0] > x1 && x[0] < x1 + dd ? sig0*pow((x[0]-x1)/dd, p) : (x[0] < 0 && x[0] > -dd ? sig0*pow((-x[0])/dd, p) : 0)', 
                  degree=3, x1=xx, dd=dPML, sig0=sig0_, p=p_)
     sig2 = fe.Expression('x[1] > x2 && x[1] < x2 + dd ? sig0*pow((x[1]-x2)/dd, p) : (x[1] < 0 && x[1] > -dd ? sig0*pow((-x[1])/dd, p) : 0)', 
                  degree=3, x2=yy, dd=dPML, sig0=sig0_, p=p_)
     
     sR = fe.as_matrix([[(1+sig1*sig2)/(1+sig1*sig1), 0.0], [0.0, (1+sig1*sig2)/(1+sig2*sig2)]])
     sI = fe.as_matrix([[(sig2-sig1)/(1+sig1*sig1), 0.0], [0.0, (sig1-sig2)/(1+sig2*sig2)]])
     cR = 1 - sig1*sig2
     cI = sig1 + sig2
     
     # define the coefficients with physical meaning
     angl_fre = self.kappa*np.pi
     angl_fre2 = fe.Constant(angl_fre*angl_fre)
     
     # define equations
     u_ = fe.TestFunction(self.V)
     du = fe.TrialFunction(self.V)
     
     u_R, u_I = fe.split(u_)
     duR, duI = fe.split(du)
     
     def sigR(v):
         return fe.dot(sR, fe.nabla_grad(v))
     def sigI(v):
         return fe.dot(sI, fe.nabla_grad(v))
     
     F1 = - fe.inner(sigR(duR)-sigI(duI), fe.nabla_grad(u_R))*(fe.dx) \
         - fe.inner(sigR(duI)+sigI(duR), fe.nabla_grad(u_I))*(fe.dx) \
         - fR*u_R*(fe.dx) - fI*u_I*(fe.dx)
     
     a2 = fe.inner(angl_fre2*q_fun*(cR*duR-cI*duI), u_R)*(fe.dx) \
          + fe.inner(angl_fre2*q_fun*(cR*duI+cI*duR), u_I)*(fe.dx) \
     
     # define boundary conditions
     def boundary(x, on_boundary):
         return on_boundary
     
     bc = [fe.DirichletBC(self.V.sub(0), fe.Constant(0.0), boundary), \
           fe.DirichletBC(self.V.sub(1), fe.Constant(0.0), boundary)]
     
     a1, L1 = fe.lhs(F1), fe.rhs(F1)
     self.u = fe.Function(self.V)
     self.A1 = fe.assemble(a1)
     self.b1 = fe.assemble(L1)
     self.A2 = fe.assemble(a2)
     bc[0].apply(self.A1, self.b1)
     bc[1].apply(self.A1, self.b1)
     bc[0].apply(self.A2)
     bc[1].apply(self.A2)
     self.A = self.A1 + self.A2
Esempio n. 16
0
 def _solve_pde(self, diff_coef):
     # Actual PDE solver for any coefficient diff_coef
     u = fe.TrialFunction(self.function_space)
     v = fe.TestFunction(self.function_space)
     a = fe.dot(diff_coef * fe.grad(u), fe.grad(v)) * fe.dx
     L = self.f * v * fe.dx
     bc = fe.DirichletBC(self.function_space, self.bc_function,
                         PoissonSolver.boundary)
     fe.solve(a == L, self.solution, bc)
Esempio n. 17
0
 def solve_problem_variational_form(self):
     u = fa.Function(self.V)
     du = fa.TrialFunction(self.V)
     v = fa.TestFunction(self.V)
     E = self._energy_density(u) * fa.dx
     dE = fa.derivative(E, u, v)
     jacE = fa.derivative(dE, u, du)
     fa.solve(dE == 0, u, self.bcs, J=jacE)
     return u
Esempio n. 18
0
def test_formulation_1_extrap_1_material():
    '''
    Test function formulation() with 1 extrinsic trap
    and 1 material
    '''
    dt = 1
    traps = [{
        "energy": 1,
        "materials": [1],
        "type": "extrinsic"
        }]
    materials = [{
            "alpha": 1,
            "beta": 2,
            "density": 3,
            "borders": [0, 1],
            "E_diff": 4,
            "D_0": 5,
            "id": 1
            }]
    
    mesh = fenics.UnitIntervalMesh(10)
    V = fenics.VectorFunctionSpace(mesh, 'P', 1, 2)
    W = fenics.FunctionSpace(mesh, 'P', 1)
    u = fenics.Function(V)
    u_n = fenics.Function(V)
    v = fenics.TestFunction(V)
    n = fenics.interpolate(fenics.Expression('1', degree=0), W)
    solutions = list(fenics.split(u))
    previous_solutions = list(fenics.split(u_n))
    testfunctions = list(fenics.split(v))
    extrinsic_traps = [n]
    mf = fenics.MeshFunction('size_t', mesh, 1, 1)
    dx = fenics.dx(subdomain_data=mf)
    temp = fenics.Expression("300", degree=0)
    flux_ = fenics.Expression("10000", degree=0)

    F, expressions = FESTIM.formulation(
        traps, extrinsic_traps, solutions, testfunctions,
        previous_solutions, dt, dx, materials, temp, flux_)
    expected_form = ((solutions[0] - previous_solutions[0]) / dt) * \
        testfunctions[0]*dx
    expected_form += 5 * fenics.exp(-4/8.6e-5/temp) * \
        fenics.dot(
            fenics.grad(solutions[0]), fenics.grad(testfunctions[0]))*dx(1)
    expected_form += -flux_*testfunctions[0]*dx + \
        ((solutions[1] - previous_solutions[1]) / dt) * \
        testfunctions[1]*dx
    expected_form += - 5 * fenics.exp(-4/8.6e-5/temp)/1/1/2 * \
        solutions[0] * (extrinsic_traps[0] - solutions[1]) * \
        testfunctions[1]*dx(1)
    expected_form += 1e13*fenics.exp(-1/8.6e-5/temp)*solutions[1] * \
        testfunctions[1]*dx(1)
    expected_form += ((solutions[1] - previous_solutions[1]) / dt) * \
        testfunctions[0]*dx

    assert expected_form.equals(F) is True
	def avg_condition_number(mesh):
		"""Computes average mesh quality based on the condition number of the reference mapping.

		This quality criterion uses the condition number (in the Frobenius norm) of the
		(linear) mapping from the elements of the mesh to the reference element. Computes
		the average of the condition number over all elements.

		Parameters
		----------
		mesh : dolfin.cpp.mesh.Mesh
			The mesh, whose quality shall be computed.

		Returns
		-------
		float
			The average mesh quality based on the condition number.
		"""

		DG0 = fenics.FunctionSpace(mesh, 'DG', 0)
		jac = Jacobian(mesh)
		inv = JacobianInverse(mesh)

		options = [
				['ksp_type', 'preonly'],
				['pc_type', 'jacobi'],
				['pc_jacobi_type', 'diagonal'],
				['ksp_rtol', 1e-16],
				['ksp_atol', 1e-20],
				['ksp_max_it', 1000]
			]
		ksp = PETSc.KSP().create()
		_setup_petsc_options([ksp], [options])

		dx = fenics.Measure('dx', mesh)
		a = fenics.TrialFunction(DG0)*fenics.TestFunction(DG0)*dx
		L = fenics.sqrt(fenics.inner(jac, jac))*fenics.sqrt(fenics.inner(inv, inv))*fenics.TestFunction(DG0)*dx

		cond = fenics.Function(DG0)

		A, b = _assemble_petsc_system(a, L)
		_solve_linear_problem(ksp, A, b, cond.vector().vec(), options)
		cond.vector().apply('')

		return np.average(np.sqrt(mesh.geometric_dimension()) / cond.vector()[:])
Esempio n. 20
0
    def fenics_p_electric(self, my_d):
        """
        @description:
            Solve poisson equation to get potential and electric field
        @Modify:
            2021/08/31
        """
        if "plugin3D" in self.det_model:
            bc_l = []
            bc_l = self.boundary_definition_3D(my_d, "Possion")
        elif "planar3D" in self.det_model:
            bc_l = self.boundary_definition_2D(my_d, "Possion")

        u = fenics.TrialFunction(self.V)
        v = fenics.TestFunction(self.V)
        if self.det_dic['name'] == "lgad3D":
            if self.det_dic['part'] == 2:
                bond = self.det_dic['bond1']
                doping_avalanche = self.f_value(my_d, self.det_dic['doping1'])
                doping = self.f_value(my_d, self.det_dic['doping2'])
                f = fenics.Expression('x[2] < width ? doping1 : doping2',
                                      degree=1,
                                      width=bond,
                                      doping1=doping_avalanche,
                                      doping2=doping)
            elif self.det_dic['part'] == 3:
                bond1 = self.det_dic['bond1']
                bond2 = self.det_dic['bond2']
                doping1 = self.f_value(my_d, self.det_dic['doping1'])
                doping2 = self.f_value(my_d, self.det_dic['doping2'])
                doping3 = self.f_value(my_d, self.det_dic['doping3'])
                f = fenics.Expression(
                    'x[2] < bonda ? dopinga : x[2] > bondb ? dopingc : dopingb',
                    degree=1,
                    bonda=bond1,
                    bondb=bond2,
                    dopinga=doping1,
                    dopingb=doping2,
                    dopingc=doping3)
            else:
                print("The structure of lgad is wrong.")
        else:
            f = fenics.Constant(self.f_value(my_d))
        a = fenics.dot(fenics.grad(u), fenics.grad(v)) * fenics.dx
        L = f * v * fenics.dx
        # Compute solution
        self.u = fenics.Function(self.V)
        fenics.solve(a == L,
                     self.u,
                     bc_l,
                     solver_parameters=dict(linear_solver='gmres',
                                            preconditioner='ilu'))
        #calculate electric field
        W = fenics.VectorFunctionSpace(self.mesh3D, 'P', 1)
        self.E_field = fenics.project(
            fenics.as_vector((self.u.dx(0), self.u.dx(1), self.u.dx(2))), W)
Esempio n. 21
0
 def compute_operators(self):
     u = fa.TrialFunction(self.V)
     v = fa.TestFunction(self.V)
     form_a = fa.inner(fa.grad(u), fa.grad(v)) * fa.dx
     form_b = u * v * fa.dx
     A = da.assemble(form_a)
     B = da.assemble(form_b)
     A_np = np.array(A.array())
     B_np = np.array(B.array())
     return A_np, B_np
Esempio n. 22
0
def forward(x):
    u = fn.TrialFunction(V)
    w = fn.TestFunction(V)
    sigma = lmbda * tr(sym(grad(u))) * Identity(2) + 2 * G * sym(
        grad(u))  # Stress
    R = simp(x) * inner(sigma, grad(w)) * dx - dot(b, w) * dx
    a, L = ufl.lhs(R), ufl.rhs(R)
    u = fa.Function(V)
    fa.solve(a == L, u, bcs)
    return u
def test_empty_measure():
    mesh, _, _, dx, ds, dS = cashocs.regular_mesh(5)
    V = fenics.FunctionSpace(mesh, 'CG', 1)
    dm = cashocs.utils.EmptyMeasure(dx)

    trial = fenics.TrialFunction(V)
    test = fenics.TestFunction(V)

    assert fenics.assemble(1 * dm) == 0.0
    assert (fenics.assemble(test * dm).norm('linf')) == 0.0
    assert (fenics.assemble(trial * test * dm).norm('linf')) == 0.0
Esempio n. 24
0
 def _solve_cell_problems(self):
     # Solves the cell problems (one for each space dimension)
     w = fe.TrialFunction(self.function_space)
     v = fe.TestFunction(self.function_space)
     a = self.a_y * fe.dot(fe.grad(w), fe.grad(v)) * fe.dx
     for i in range(self.dim):
         L = fe.div(self.a_y * self.e_is[i]) * v * fe.dx
         bc = fe.DirichletBC(self.function_space, self.bc_function,
                             PoissonSolver.boundary)
         fe.solve(a == L, self.cell_solutions[i], bc)
         fe.plot(self.cell_solutions[i])
Esempio n. 25
0
    def create_bilinear_form_and_rhs(self):

        # Define variational problem
        u = fe.TrialFunction(self.function_space)
        v = fe.TestFunction(self.function_space)

        self.bilinear_form = (1 + self.lam * self.dt) *\
                (u * v * fe.dx) + self.dt * self.diffusion_coefficient *\
                (fe.dot(fe.grad(u), fe.grad(v)) * fe.dx)

        self.rhs = (self.u_n + self.dt * self.rhs_fun * self.u_n) * v * fe.dx
Esempio n. 26
0
def calTrueSol(para):
    nx, ny = para['mesh_N'][0], para['mesh_N'][1]
    mesh = fe.UnitSquareMesh(nx, ny)
    Vu = fe.FunctionSpace(mesh, 'P', para['P'])
    Vc = fe.FunctionSpace(mesh, 'P', para['P'])
    al = fe.Constant(para['alpha'])
    f = fe.Expression(para['f'], degree=5)
    q1 = fe.interpolate(fe.Expression(para['q1'], degree=5), Vc)
    q2 = fe.interpolate(fe.Expression(para['q2'], degree=5), Vc)
    q3 = fe.interpolate(fe.Expression(para['q3'], degree=5), Vc)
    theta = fe.interpolate(fe.Expression(para['q4'], degree=5), Vc)

    class BoundaryX0(fe.SubDomain):
        def inside(self, x, on_boundary):
            return on_boundary and fe.near(x[0], 0.0)

    class BoundaryX1(fe.SubDomain):
        def inside(self, x, on_boundary):
            return on_boundary and fe.near(x[0], 1.0)

    class BoundaryY0(fe.SubDomain):
        def inside(self, x, on_boundary):
            return on_boundary and fe.near(x[1], 0.0)

    class BoundaryY1(fe.SubDomain):
        def inside(self, x, on_boundary):
            return on_boundary and fe.near(x[1], 1.0)

    boundaries = fe.MeshFunction('size_t', mesh, mesh.topology().dim() - 1)
    boundaries.set_all(0)
    bc0, bc1, bc2, bc3 = BoundaryX0(), BoundaryX1(), BoundaryY0(), BoundaryY1()
    bc0.mark(boundaries, 1)
    bc1.mark(boundaries, 2)
    bc2.mark(boundaries, 3)
    bc3.mark(boundaries, 4)

    domains = fe.MeshFunction("size_t", mesh, mesh.topology().dim())
    domains.set_all(0)

    bcD = fe.DirichletBC(Vu, theta, boundaries, 4)
    dx = fe.Measure('dx', domain=mesh, subdomain_data=domains)
    ds = fe.Measure('ds', domain=mesh, subdomain_data=boundaries)

    u_trial, u_test = fe.TrialFunction(Vu), fe.TestFunction(Vu)
    u = fe.Function(Vu)
    left = fe.inner(al * fe.nabla_grad(u_trial), fe.nabla_grad(u_test)) * dx
    right = f * u_test * dx + (q1 * u_test * ds(1) + q2 * u_test * ds(2) +
                               q3 * u_test * ds(3))

    left_m, right_m = fe.assemble_system(left, right, bcD)
    fe.solve(left_m, u.vector(), right_m)

    return u
Esempio n. 27
0
    def __init__(self, mesh, constitutive_model):

        W = fe.FunctionSpace(mesh, "DG", 1)
        super().__init__(mesh, constitutive_model, W)

        self.w = fe.Function(W)
        self.p, self.p0 = self.w, fe.Function(W)

        self.g = fe.TestFunction(W)

        self.functional = fe.inner(self.p, self.g) - fe.inner(
            self.constitutive_model)
Esempio n. 28
0
 def mesh_gen_default(self, intervals, typ='P', order=1):
     """
     creates a square with sides of 1, divided by intervals
     by default the type of the volume associated with the mesh
     is considered to be Lagrangian, with order 1.
     """
     self._mesh = FEN.UnitSquareMesh(intervals, intervals)
     self.input['mesh'] = self._mesh
     self._V = FEN.FunctionSpace(self._mesh, typ, order)
     self.input['V'] = self._V
     self._u = FEN.TrialFunction(self._V)
     self._v = FEN.TestFunction(self._V)
Esempio n. 29
0
def dynamic_solver_func(ncells=10,  # количество узлов на заданном итервале
                        init_time=0,  # начальный момент времени
                        end_time=10,  # конечный момент времени
                        dxdphi=1,  # производная от потенциала по х
                        dydphi=1,  # производня от потенциала по у
                        x0=0,  # начальное положение по оси х
                        vx0=1,  # проекция начальной скорости на ось х
                        y0=0,  # начальное положение по оси у
                        vy0=1):  # проекция начальной скорости на ось у
    """ Функция на вход которой подается производная от потенциала
        гравитационного поля, возвращающая координаты смещенных
        материальных точек (частиц).
    """
    # генерация сетки на заданном интервале времени
    mesh = fen.IntervalMesh(ncells, 0, end_time-init_time)

    welm = fen.MixedElement([fen.FiniteElement('Lagrange', fen.interval, 2),
                             fen.FiniteElement('Lagrange', fen.interval, 2),
                             fen.FiniteElement('Lagrange', fen.interval, 2),
                             fen.FiniteElement('Lagrange', fen.interval, 2)])

    # генерация функционального рростаанства
    W = fen.FunctionSpace(mesh, welm)

    # постановка начальных условий задачи
    bcsys = [fen.DirichletBC(W.sub(0), fen.Constant(x0), 'near(x[0], 0)'),
             fen.DirichletBC(W.sub(1), fen.Constant(vx0), 'near(x[0], 0)'),
             fen.DirichletBC(W.sub(2), fen.Constant(y0), 'near(x[0], 0)'),
             fen.DirichletBC(W.sub(3), fen.Constant(vy0), 'near(x[0], 0)')]

    # опееделение тестовых функций для решения задачи
    up = fen.Function(W)
    x_cor, v_x, y_cor, v_y = fen.split(up)
    v1, v2, v3, v4 = fen.split(fen.TestFunction(W))

    # постановка задачи drdt = v; dvdt = - grad(phi) в проекциях на оси системы координат
    weak_form = (x_cor.dx(0) - v_x) * v1 * fen.dx + (v_x.dx(0) + dxdphi) * v2 * fen.dx \
                + (y_cor.dx(0) - v_y) * v3 * fen.dx + (v_y.dx(0) + dydphi) * v4 * fen.dx

    # решние поставленной задачи
    fen.solve(weak_form == 0, up, bcs=bcsys)

    # определение момента времени
    time = fen.Point(end_time - init_time)

    # расчет координат и скоростей
    x_end_time = up(time.x())[0]
    vx_end_time = up(time.x())[1]
    y_end_time = up(time.x())[2]
    vy_end_time = up(time.x())[3]

    return x_end_time, y_end_time, vx_end_time, vy_end_time
Esempio n. 30
0
    def solve_problem_weak_form(self):
        u = fa.Function(self.V)
        du = fa.TrialFunction(self.V)
        v = fa.TestFunction(self.V)
        F = fa.inner(fa.grad(u), fa.grad(v)) * fa.dx - self.source * v * fa.dx
        J = fa.derivative(F, u, du)

        # The problem in this case is indeed linear, but using a nonlinear
        # solver doesn't hurt
        problem = fa.NonlinearVariationalProblem(F, u, self.bcs, J)
        solver = fa.NonlinearVariationalSolver(problem)
        solver.solve()
        return u