Example #1
0
 def __init__(self, element):
     cell = element.cell()
     degree = element.degree()
     family = lambda c: "DG" if c.is_simplex() else "DQ"
     if isinstance(cell, ufl.TensorProductCell):
         scalar_element = ufl.TensorProductElement(
             *(ufl.FiniteElement(family(c), cell=c, degree=d)
               for (c, d) in zip(cell.sub_cells(), degree)))
     else:
         scalar_element = ufl.FiniteElement(family(cell),
                                            cell=cell,
                                            degree=degree)
     shape = element.value_shape()
     if len(shape) == 0:
         DG = scalar_element
     elif len(shape) == 1:
         shape, = shape
         DG = ufl.VectorElement(scalar_element, dim=shape)
     else:
         DG = ufl.TensorElement(scalar_element, shape=shape)
     self.embedding_element = DG
     self._V_DG_mass = {}
     self._DG_inv_mass = {}
     self._V_approx_inv_mass = {}
     self._V_inv_mass_ksp = {}
     self._DG_work = {}
     self._work_vec = {}
     self._V_dof_weights = {}
Example #2
0
def TensorFunctionSpace(mesh, family, degree=None, shape=None,
                        symmetry=None, name=None, vfamily=None,
                        vdegree=None):
    """Create a rank-2 :class:`.FunctionSpace`.

    :arg mesh: The mesh to determine the cell from.
    :arg family: The finite element family.
    :arg degree: The degree of the finite element.
    :arg shape: An optional shape for the tensor-valued degrees of
       freedom at each function space node (defaults to a square
       tensor using the geometric dimension of the mesh).
    :arg symmetry: Optional symmetries in the tensor value.
    :arg name: An optional name for the function space.
    :arg vfamily: The finite element in the vertical dimension
        (extruded meshes only).
    :arg vdegree: The degree of the element in the vertical dimension
        (extruded meshes only).

    The ``family`` argument may be an existing
    :class:`~ufl.classes.FiniteElementBase`, in which case all other arguments
    are ignored and the appropriate :class:`.FunctionSpace` is
    returned.  In this case, the provided element must have an empty
    :meth:`~ufl.classes.FiniteElementBase.value_shape`.

    .. note::

       The element that you provide must be a scalar element (with
       empty ``value_shape``).  If you already have an existing
       :class:`~ufl.classes.TensorElement`, you should pass it to
       :func:`FunctionSpace` directly instead.
    """
    sub_element = make_scalar_element(mesh, family, degree, vfamily, vdegree)
    shape = shape or (mesh.ufl_cell().geometric_dimension(),) * 2
    element = ufl.TensorElement(sub_element, shape=shape, symmetry=symmetry)
    return FunctionSpace(mesh, element, name=name)
Example #3
0
    def __new__(cls,
                mesh,
                family,
                degree=None,
                shape=None,
                symmetry=None,
                name=None,
                vfamily=None,
                vdegree=None):
        mesh.init()
        mesh_t = mesh.topology

        # TensorFunctionSpace shape defaults to the (gdim, gdim)
        shape = shape or (mesh.ufl_cell().geometric_dimension(), ) * 2

        if isinstance(mesh_t.ufl_cell(), ufl.OuterProductCell):
            raise NotImplementedError(
                "TensorFunctionSpace on extruded meshes not implemented")
        else:
            element = ufl.TensorElement(family,
                                        cell=mesh_t.ufl_cell(),
                                        degree=degree,
                                        shape=shape,
                                        symmetry=symmetry)

        self = super(TensorFunctionSpace, cls).__new__(cls,
                                                       mesh_t,
                                                       element,
                                                       name=name,
                                                       shape=shape)
        if mesh is not mesh_t:
            self = WithGeometry(self, mesh)
        return self
Example #4
0
    def __init__(self, value, cell=None, name=None):
        """
        Create constant-valued function with given value.

        *Arguments*
            value
                The value may be either a single scalar value, or a
                tuple/list of values for vector-valued functions, or
                nested lists or a numpy array for tensor-valued
                functions.
            cell
                Optional argument. A :py:class:`Cell
                <ufl.Cell>` which defines the geometrical
                dimensions the Constant is defined for.
            name
                Optional argument. A str which overrules the default
                name of the Constant.

        The data type Constant represents a constant value that is
        unknown at compile-time. Its values can thus be changed
        without requiring re-generation and re-compilation of C++
        code.

        *Examples of usage*

            .. code-block:: python

                p = Constant(pi/4)              # scalar
                C = Constant((0.0, -1.0, 0.0))  # constant vector

        """

        # TODO: Either take mesh instead of cell, or drop cell and let
        # grad(c) be undefined.
        if cell is not None:
            cell = ufl.as_cell(cell)
        ufl_domain = None

        array = numpy.array(value)
        rank = len(array.shape)
        floats = list(map(float, array.flat))

        # Create UFL element and initialize constant
        if rank == 0:
            ufl_element = ufl.FiniteElement("Real", cell, 0)
            cpp.Constant.__init__(self, floats[0])
        elif rank == 1:
            ufl_element = ufl.VectorElement("Real", cell, 0, dim=len(floats))
            cpp.Constant.__init__(self, floats)
        else:
            ufl_element = ufl.TensorElement("Real", cell, 0, shape=array.shape)
            cpp.Constant.__init__(self, list(array.shape), floats)

        # Initialize base classes
        ufl_function_space = ufl.FunctionSpace(ufl_domain, ufl_element)
        ufl.Coefficient.__init__(self, ufl_function_space, count=self.id())

        # Set name as given or automatic
        name = name or "f_%d" % self.count()
        self.rename(name, "a Constant")
Example #5
0
def test_tensor_element(compile_args):
    ufl_element = ufl.TensorElement("Lagrange", ufl.triangle, 1)
    jit_compiled_elements, module, code = ffcx.codegeneration.jit.compile_elements(
        [ufl_element], cffi_extra_compile_args=compile_args)
    ufc_element, ufc_dofmap = jit_compiled_elements[0]

    assert ufc_element.topological_dimension == 2
    assert ufc_element.geometric_dimension == 2
    assert ufc_element.space_dimension == 12
    assert ufc_element.value_rank == 2
    assert ufc_element.value_shape[0] == 2
    assert ufc_element.value_shape[1] == 2
    assert ufc_element.value_size == 4
    assert ufc_element.reference_value_rank == 2
    assert ufc_element.reference_value_shape[0] == 2
    assert ufc_element.reference_value_shape[1] == 2
    assert ufc_element.reference_value_size == 4
    assert ufc_element.block_size == 4
    assert ufc_element.num_sub_elements == 4

    assert ufc_dofmap.block_size == 4
    assert ufc_dofmap.num_global_support_dofs == 0
    assert ufc_dofmap.num_global_support_dofs == 0
    assert ufc_dofmap.num_element_support_dofs == 3
    assert ufc_dofmap.num_entity_dofs[0] == 1
    assert ufc_dofmap.num_entity_dofs[1] == 0
    assert ufc_dofmap.num_entity_dofs[2] == 0
    assert ufc_dofmap.num_entity_dofs[3] == 0
    for v in range(3):
        vals = np.zeros(1, dtype=np.int32)
        vals_ptr = module.ffi.cast("int *", module.ffi.from_buffer(vals))
        ufc_dofmap.tabulate_entity_dofs(vals_ptr, 0, v)
        assert vals[0] == v
    assert ufc_dofmap.num_sub_dofmaps == 4
Example #6
0
def test_save_1d_tensor(tempdir):
    mesh = create_unit_interval(MPI.COMM_WORLD, 32)
    element = ufl.TensorElement("Lagrange", mesh.ufl_cell(), 2, shape=(2, 2))
    u = Function(FunctionSpace(mesh, element))
    u.x.array[:] = 1.0
    filename = os.path.join(tempdir, "u.pvd")
    with VTKFile(mesh.comm, filename, "w") as vtk:
        vtk.write_function(u, 0.)
Example #7
0
def test_save_1d_tensor(tempdir):
    mesh = UnitIntervalMesh(MPI.COMM_WORLD, 32)
    element = ufl.TensorElement("Lagrange", mesh.ufl_cell(), 2, shape=(2, 2))
    u = Function(FunctionSpace(mesh, element))
    with u.vector.localForm() as loc:
        loc.set(1.0)
    filename = os.path.join(tempdir, "u.pvd")
    with VTKFile(mesh.mpi_comm(), filename, "w") as vtk:
        vtk.write_function(u, 0.)
Example #8
0
def TensorFunctionSpace(mesh: cpp.mesh.Mesh,
                        element: ElementMetaData,
                        shape=None,
                        symmetry: bool = None,
                        restriction=None):
    """Create tensor finite element (composition of scalar elements) function space."""

    e = ElementMetaData(*element)
    ufl_element = ufl.TensorElement(e.family, mesh.ufl_cell(), e.degree, shape, symmetry)
    return FunctionSpace(mesh, ufl_element)
def TensorFunctionSpace(mesh, family, degree, shape=None, symmetry=None,
                        constrained_domain=None, restriction=None):
    """Create finite element function space."""

    # Create UFL element
    element = ufl.TensorElement(family, mesh.ufl_cell(), degree,
                                shape, symmetry)

    # Return (Py)DOLFIN FunctionSpace
    return FunctionSpace(mesh, element, constrained_domain=constrained_domain)
Example #10
0
def MultiMeshTensorFunctionSpace(multimesh, family, degree, shape=None,
                                 symmetry=None):
    """Create finite element MultiMesh function space."""

    # Create UFL element
    mesh = multimesh.part(0)
    element = ufl.TensorElement(family, mesh.ufl_cell(), degree,
                                shape, symmetry)

    # Return (Py)DOLFIN FunctionSpace
    return MultiMeshFunctionSpace(mesh, element)
Example #11
0
def TensorFunctionSpace(mesh,
                        element,
                        shape=None,
                        symmetry=None,
                        name='fspace',
                        si=0,
                        parent=None):
    sub_element = make_scalar_element(element)
    shape = shape or (mesh.ufl_cell().geometric_dimension(),
                      mesh.ufl_cell().geometric_dimension())
    element = ufl.TensorElement(sub_element, shape=shape, symmetry=symmetry)
    return FunctionSpace(mesh, element, name=name)
Example #12
0
def reconstruct_element(element, cell=None):
    """Rebuild element with a new cell."""
    if cell is None:
        return element
    if isinstance(element, ufl.FiniteElement):
        family = element.family()
        degree = element.degree()
        return ufl.FiniteElement(family, cell, degree)
    if isinstance(element, ufl.VectorElement):
        family = element.family()
        degree = element.degree()
        dim = len(element.sub_elements())
        return ufl.VectorElement(family, cell, degree, dim)
    if isinstance(element, ufl.TensorElement):
        family = element.family()
        degree = element.degree()
        shape = element.value_shape()
        symmetry = element.symmetry()
        return ufl.TensorElement(family, cell, degree, shape, symmetry)
    if isinstance(element, ufl.EnrichedElement):
        eles = [
            reconstruct_element(sub, cell=cell) for sub in element._elements
        ]
        return ufl.EnrichedElement(*eles)
    if isinstance(element, ufl.RestrictedElement):
        return ufl.RestrictedElement(
            reconstruct_element(element.sub_element(), cell=cell),
            element.restriction_domain())
    if isinstance(element,
                  (ufl.TraceElement, ufl.InteriorElement, ufl.HDivElement,
                   ufl.HCurlElement, ufl.BrokenElement, ufl.FacetElement)):
        return type(element)(reconstruct_element(element._element, cell=cell))
    if isinstance(element, ufl.OuterProductElement):
        return ufl.OuterProductElement(element._A, element._B, cell=cell)
    if isinstance(element, ufl.OuterProductVectorElement):
        dim = len(element.sub_elements())
        return ufl.OuterProductVectorElement(element._A,
                                             element._B,
                                             cell=cell,
                                             dim=dim)
    if isinstance(element, ufl.OuterProductTensorElement):
        return element.reconstruct(cell=cell)
    if isinstance(element, ufl.MixedElement):
        eles = [
            reconstruct_element(sub, cell=cell)
            for sub in element.sub_elements()
        ]
        return ufl.MixedElement(*eles)
    raise NotImplementedError(
        "Don't know how to reconstruct element of type %s" % type(element))
Example #13
0
def test_tensor_element(compile_args):
    ufl_element = ufl.TensorElement("Lagrange", ufl.triangle, 1)
    jit_compiled_elements, module = ffcx.codegeneration.jit.compile_elements(
        [ufl_element], cffi_extra_compile_args=compile_args)
    ufc_element, ufc_dofmap = jit_compiled_elements[0]

    assert ufc_element.topological_dimension == 2
    assert ufc_element.geometric_dimension == 2
    assert ufc_element.space_dimension == 12
    assert ufc_element.value_rank == 2
    assert ufc_element.value_dimension(0) == 2
    assert ufc_element.value_dimension(1) == 2
    assert ufc_element.value_dimension(2) == 1
    assert ufc_element.value_size == 4
    assert ufc_element.reference_value_rank == 2
    assert ufc_element.reference_value_dimension(0) == 2
    assert ufc_element.reference_value_dimension(1) == 2
    assert ufc_element.reference_value_dimension(2) == 1
    assert ufc_element.reference_value_size == 4
    assert ufc_element.block_size == 4
    X = np.array([[0.0, 0.0], [0.5, 0.5]])
    npoint = X.shape[0]
    X_ptr = module.ffi.cast("const double *", module.ffi.from_buffer(X))
    vals = np.zeros((npoint, 3, 1))
    vals_ptr = module.ffi.cast("double *", module.ffi.from_buffer(vals))
    ufc_element.evaluate_reference_basis(vals_ptr, npoint, X_ptr)
    assert np.allclose(vals, [[[1], [0], [0]], [[0], [.5], [.5]]])
    vals = np.zeros(6)
    vals_ptr = module.ffi.cast("double *", module.ffi.from_buffer(vals))
    ufc_element.tabulate_reference_dof_coordinates(vals_ptr)
    assert np.allclose(vals, [0, 0, 1, 0, 0, 1])
    assert ufc_element.num_sub_elements == 4

    assert ufc_dofmap.block_size == 4
    assert ufc_dofmap.num_global_support_dofs == 0
    assert ufc_dofmap.num_global_support_dofs == 0
    assert ufc_dofmap.num_element_support_dofs == 3
    assert ufc_dofmap.num_entity_dofs[0] == 1
    assert ufc_dofmap.num_entity_dofs[1] == 0
    assert ufc_dofmap.num_entity_dofs[2] == 0
    assert ufc_dofmap.num_entity_dofs[3] == 0
    for v in range(3):
        vals = np.zeros(1, dtype=np.int)
        vals_ptr = module.ffi.cast("int *", module.ffi.from_buffer(vals))
        ufc_dofmap.tabulate_entity_dofs(vals_ptr, 0, v)
        assert vals[0] == v
    assert ufc_dofmap.num_sub_dofmaps == 4
    assert ufc_dofmap.size_base_permutations == 9
    for i, j in enumerate([0, 1, 2, 0, 1, 2, 0, 1, 2]):
        assert ufc_dofmap.base_permutations[i] == j
Example #14
0
    def __init__(self, value):

        self.dat, rank, shape = _globalify(value)

        cell = None
        domain = None
        if rank == 0:
            e = ufl.FiniteElement("Real", cell, 0)
        elif rank == 1:
            e = ufl.VectorElement("Real", cell, 0, shape[0])
        elif rank == 2:
            e = ufl.TensorElement("Real", cell, 0, shape=shape)

        fs = ufl.FunctionSpace(domain, e)
        super(Constant, self).__init__(fs)
        self._repr = 'Constant(%r, %r)' % (self.ufl_element(), self.count())
Example #15
0
    def __init__(self, mesh, family, degree, shape=None, symmetry=None, \
                 constrained_domain=None, restriction=None):
        """
        Create tensor-valued finite element function space.

        *Arguments*
            mesh
                a :py:class:`Mesh <dolfin.cpp.Mesh>`.
            family
                a string specifying the element family,
                see :py:class:`FunctionSpace
                <dolfin.functions.functionspace.FunctionSpace>`
                for alternatives.
            degree
                the degree of the element.
            shape
                an optional argument specifying the shape of the tensor.
            symmetry
                optional argument specifying whether the tensor is symmetric.

        If the shape argument is not provided, the dimension will be deduced from
        the dimension of the mesh.

        *Example of usage*

            .. code-block:: python

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

        """

        # Get ufl cell from Mesh or Restriction
        # FIXME: Get a ufl.Domain instead of cell somehow.
        cell = mesh.ufl_cell() if isinstance(mesh, cpp.Mesh) else mesh.mesh().ufl_cell()

        # TODO: Is this necessary? Doesn't ufl handle dim=None the same way?
        if shape is None:
            dim = cell.geometric_dimension()
            shape = (dim, dim)

        # Create element
        element = ufl.TensorElement(family, cell, degree, shape, symmetry)
        if restriction is not None:
            element = element[restriction]

        # Initialize base class
        FunctionSpaceBase.__init__(self, mesh, element, constrained_domain=constrained_domain)
Example #16
0
    def __init__(self, value, domain=None):
        # Init also called in mesh constructor, but constant can be built without mesh
        utils._init()
        try:
            domain.init()
        except AttributeError:
            pass
        self.dat, rank, shape = _globalify(value)

        if rank == 0:
            e = ufl.FiniteElement("Real", domain, 0)
        elif rank == 1:
            e = ufl.VectorElement("Real", domain, 0, shape[0])
        elif rank == 2:
            e = ufl.TensorElement("Real", domain, 0, shape=shape)
        super(Constant, self).__init__(e)
        self._ufl_element = self.element()
        self._repr = 'Constant(%r, %r)' % (self._ufl_element, self.count())
Example #17
0
    def __init__(self, value, domain=None):
        # Init also called in mesh constructor, but constant can be built without mesh
        utils._init()
        self.dat, rank, shape = _globalify(value)

        cell = None
        if domain is not None:
            domain = ufl.as_domain(domain)
            cell = domain.ufl_cell()
        if rank == 0:
            e = ufl.FiniteElement("Real", cell, 0)
        elif rank == 1:
            e = ufl.VectorElement("Real", cell, 0, shape[0])
        elif rank == 2:
            e = ufl.TensorElement("Real", cell, 0, shape=shape)

        fs = ufl.FunctionSpace(domain, e)
        super(Constant, self).__init__(fs)
        self._repr = 'Constant(%r, %r)' % (self.ufl_element(), self.count())
Example #18
0
    def __init__(self, mesh, family, degree, shape=None, symmetry=None, \
                 constrained_domain=None, restriction=None):
        """Create tensor-valued finite element function space.

        *Arguments*
            mesh
                a :py:class:`Mesh <dolfin.cpp.Mesh>`.
            family
                a string specifying the element family,
                see :py:class:`FunctionSpace
                <dolfin.functions.functionspace.FunctionSpace>`
                for alternatives.
            degree
                the degree of the element.
            shape
                an optional argument specifying the shape of the tensor.
            symmetry
                optional argument specifying whether the tensor is symmetric.

        If the shape argument is not provided, the dimension will be
        deduced from the dimension of the mesh.

        *Example of usage*

            .. code-block:: python

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

        """

        # Get Mesh or Restriction from Domain or Domain from Mesh or
        # Restriction
        ufl_domain, mesh = _analyse_mesh_argument(mesh)

        # Create element
        element = ufl.TensorElement(family, ufl_domain, degree, shape,
                                    symmetry)
        if restriction is not None:
            element = element[restriction]

        # Initialize base class
        FunctionSpaceBase.__init__(self, mesh, element, \
                                   constrained_domain=constrained_domain)
Example #19
0
def _select_element(family, cell, degree, value_shape):
    """Select finite element type for cases where user has not provided a
    complete ufl.FiniteElement

    """
    if family is None:
        if degree == 0:
            family = "Discontinuous Lagrange"
        else:
            family = "Lagrange"

    if len(value_shape) == 0:
        element = ufl.FiniteElement(family, cell, degree)
    elif len(value_shape) == 1:
        element = ufl.VectorElement(family, cell, degree, dim=value_shape[0])
    else:
        element = ufl.TensorElement(family, cell, degree, shape=value_shape)

    return element
Example #20
0
def TensorFunctionSpace(mesh,
                        family,
                        degree,
                        shape=None,
                        symmetry=None,
                        constrained_domain=None,
                        restriction=None):
    """Create tensor-valued finite element function space.

    *Arguments*
        mesh
            a :py:class:`Mesh <dolfin.cpp.Mesh>`.
        family
            a string specifying the element family,
            see :py:class:`FunctionSpace
            <dolfin.functions.functionspace.FunctionSpace>`
            for alternatives.
        degree
            the degree of the element.
        shape
            an optional argument specifying the shape of the tensor.
        symmetry
            optional argument specifying whether the tensor is symmetric.

    If the shape argument is not provided, the dimension will be
    deduced from the dimension of the mesh.

    *Example of usage*

        .. code-block:: python

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

    """
    # Create element
    element = ufl.TensorElement(family, mesh.ufl_cell(), degree, shape,
                                symmetry)
    if restriction is not None:
        element = element[restriction]

    return FunctionSpace(mesh, element, constrained_domain=constrained_domain)
Example #21
0
    def _process_args(cls,
                      mesh,
                      family,
                      degree,
                      shape=None,
                      symmetry=None,
                      vfamily=None,
                      vdegree=None,
                      **kwargs):
        # TensorFunctionSpace shape defaults to the (gdim, gdim)
        shape = shape or (mesh.ufl_cell().geometric_dimension(), ) * 2

        if isinstance(mesh, mesh_t.ExtrudedMesh):
            raise NotImplementedError("TFS on extruded meshes not implemented")
        else:
            element = ufl.TensorElement(family,
                                        domain=mesh.ufl_cell(),
                                        degree=degree,
                                        shape=shape,
                                        symmetry=symmetry)
        return (mesh, mesh, element), dict(kwargs, shape=shape)
Example #22
0
    def __init__(self, element, use_fortin_interpolation=True):
        degree = element.degree()
        cell = element.cell()
        shape = element.value_shape()
        if len(shape) == 0:
            DG = ufl.FiniteElement("DG", cell, degree)
        elif len(shape) == 1:
            shape, = shape
            DG = ufl.VectorElement("DG", cell, degree, dim=shape)
        else:
            DG = ufl.TensorElement("DG", cell, degree, shape=shape)

        self.embedding_element = DG
        self.use_fortin_interpolation = use_fortin_interpolation
        self._V_DG_mass = {}
        self._DG_inv_mass = {}
        self._V_approx_inv_mass = {}
        self._V_inv_mass_ksp = {}
        self._DG_work = {}
        self._work_vec = {}
        self._V_dof_weights = {}
Example #23
0
    def __init__(self, value, cell, name=None, symmetry=None):

        cell = ufl.as_cell(cell)
        ufl_domain = None

        array = numpy.array(value)
        rank = len(array.shape)
        floats = list(map(float, array.flat))

        assert rank == 2

        ufl_element = ufl.TensorElement("Real",
                                        cell,
                                        0,
                                        shape=array.shape,
                                        symmetry=symmetry)
        cpp.Constant.__init__(self, list(array.shape), floats)

        ufl_function_space = ufl.FunctionSpace(ufl_domain, ufl_element)
        ufl.Coefficient.__init__(self, ufl_function_space, count=self.id())

        name = name or "f_%d" % self.count()
        self.rename(name, "a Constant")
import ufl
from dolfinx.fem import locate_dofs_topological
from dolfinx.mesh import locate_entities_boundary
from mpi4py import MPI
from petsc4py import PETSc

filedir = os.path.dirname(__file__)
infile = dolfinx.io.XDMFFile(MPI.COMM_WORLD,
                             os.path.join(filedir, "cooks_tri_mesh.xdmf"),
                             "r",
                             encoding=dolfinx.cpp.io.XDMFFile.Encoding.ASCII)
mesh = infile.read_mesh(name="Grid")
infile.close()

# Stress (Se) and displacement (Ue) elements
Se = ufl.TensorElement("DG", mesh.ufl_cell(), 1, symmetry=True)
Ue = ufl.VectorElement("CG", mesh.ufl_cell(), 2)

S = dolfinx.FunctionSpace(mesh, Se)
U = dolfinx.FunctionSpace(mesh, Ue)

# Get local dofmap sizes for later local tensor tabulations
Ssize = S.dolfin_element().space_dimension()
Usize = U.dolfin_element().space_dimension()

sigma, tau = ufl.TrialFunction(S), ufl.TestFunction(S)
u, v = ufl.TrialFunction(U), ufl.TestFunction(U)


def free_end(x):
    """Marks the leftmost points of the cantilever"""
    return μ.value * np.array(
        [l0 * 0.01 * np.sign(x[0]), 0.0 * x[1], 0.0 * x[2]])


# Define integration measures
quad_degree = p
dx = ufl.Measure("dx",
                 domain=mesh,
                 subdomain_data=subdomains,
                 metadata={"quadrature_degree": quad_degree})

# Function spaces
Ve = ufl.VectorElement("CG", mesh.ufl_cell(), p)
Te = ufl.TensorElement("Quadrature",
                       mesh.ufl_cell(),
                       degree=quad_degree,
                       quad_scheme="default",
                       symmetry=True)
Se = ufl.FiniteElement("Quadrature",
                       mesh.ufl_cell(),
                       degree=quad_degree,
                       quad_scheme="default")

Vf = dolfinx.fem.FunctionSpace(mesh, Ve)
Tf = dolfinx.fem.FunctionSpace(mesh, Te)
Sf = dolfinx.fem.FunctionSpace(mesh, Se)

# Define functions
u = dolfinx.fem.Function(Vf, name="u")  # displacement
P = dolfinx.fem.Function(Tf, name="P")  # plastic strain
h = dolfinx.fem.Function(Sf, name="h")  # isotropic hardening
Example #26
0
def initialize_functions(mesh):

    STRESS_elem = ufl.TensorElement("DG", mesh.ufl_cell(),
                                    args.disp_degree - 1)
    DMG_elem = ufl.FiniteElement("Quadrature",
                                 mesh.ufl_cell(),
                                 degree=quad_degree_stress,
                                 quad_scheme="default")

    # Space for dashpot viscosity should ideally be Quadrature, but this wouldn't
    # work since we use it to update other non-Quadrature functions
    ETA_DASH_elem = ufl.FiniteElement("DG", mesh.ufl_cell(), 2)
    DISPL_elem = ufl.VectorElement("CG", mesh.ufl_cell(), args.disp_degree)
    TEMP_elem = ufl.FiniteElement("CG", mesh.ufl_cell(), temp_degree)
    HUM_elem = ufl.FiniteElement("CG", mesh.ufl_cell(), hum_degree)
    CO2_elem = ufl.FiniteElement("CG", mesh.ufl_cell(), co2_degree)

    STRESS = FunctionSpace(mesh, STRESS_elem)
    DMG = FunctionSpace(mesh, DMG_elem)
    ETA_DASH = FunctionSpace(mesh, ETA_DASH_elem)
    DISPL = FunctionSpace(mesh, DISPL_elem)
    TEMP = FunctionSpace(mesh, TEMP_elem)
    HUM = FunctionSpace(mesh, HUM_elem)
    CO2 = FunctionSpace(mesh, CO2_elem)

    W = []
    W.append(DISPL)
    W.append(TEMP)
    W.append(HUM)
    W.append(CO2)

    # Initial temperature
    temp0 = Function(W[1], name="temp0")
    temp1 = Function(W[1], name="temp1")

    # Initial humidity
    phi0 = Function(W[2], name="phi0")
    phi1 = Function(W[2], name="phi1")

    # Initial CO2 concentration
    co20 = Function(W[3], name="co20")
    co21 = Function(W[3], name="co21")

    # Displacement
    displ0 = Function(W[0], name="displ0")
    displ1 = Function(W[0], name="displ1")

    # Pack all internal variables
    # This is done just for brevity of solve method interface
    intern_var0 = OrderedDict()
    intern_var0["eta_dash"] = Function(ETA_DASH)
    intern_var0["caco3"] = Function(CO2, name="caco3")

    intern_var0["eps_cr_kel"] = Function(STRESS, name="eps_cr_kel")
    intern_var0["eps_cr_dash"] = Function(STRESS, name="eps_cr_dash")
    intern_var0["eps_sh_dr"] = Function(STRESS)
    intern_var0["eps_th"] = Function(STRESS)
    intern_var0["eps_eqv"] = Function(DMG, name="eps_eqv")
    intern_var0["sigma"] = Function(STRESS, name="sigma")
    intern_var0["dmg"] = Function(DMG, name="dmg")

    for i in range(mps.M):
        intern_var0[f"gamma_{i}"] = Function(STRESS)

    intern_var1 = OrderedDict()
    intern_var1["eta_dash"] = Function(intern_var0["eta_dash"].function_space)
    intern_var1["caco3"] = Function(intern_var0["caco3"].function_space)
    intern_var1["eps_cr_kel"] = Function(
        intern_var0["eps_cr_kel"].function_space)
    intern_var1["eps_cr_dash"] = Function(
        intern_var0["eps_cr_dash"].function_space)
    intern_var1["eps_sh_dr"] = Function(
        intern_var0["eps_sh_dr"].function_space)
    intern_var1["eps_th"] = Function(intern_var0["eps_th"].function_space)
    intern_var1["eps_eqv"] = Function(intern_var0["eps_eqv"].function_space)
    intern_var1["sigma"] = Function(intern_var0["sigma"].function_space)
    intern_var1["dmg"] = Function(intern_var0["dmg"].function_space)

    for i in range(mps.M):
        intern_var1[f"gamma_{i}"] = Function(
            intern_var0[f"gamma_{i}"].function_space)

    # Pack all "solved-for" quantities
    w0 = OrderedDict()
    w0["displ"] = displ0
    w0["temp"] = temp0
    w0["phi"] = phi0
    w0["co2"] = co20

    # Pack all "solved-for" quantities
    w1 = OrderedDict()
    w1["displ"] = displ1
    w1["temp"] = temp1
    w1["phi"] = phi1
    w1["co2"] = co21

    return w0, w1, intern_var0, intern_var1
Example #27
0
    def __init__(self, value, cell=None, name=None):
        """
        Create constant-valued function with given value.

        *Arguments*
            value
                The value may be either a single scalar value, or a
                tuple/list of values for vector-valued functions, or
                nested lists or a numpy array for tensor-valued
                functions.
            cell
                Optional argument. A :py:class:`Cell
                <ufl.Cell>` which defines the geometrical
                dimensions the Constant is defined for.
            name
                Optional argument. A str which overrules the default
                name of the Constant.

        The data type Constant represents a constant value that is
        unknown at compile-time. Its values can thus be changed
        without requiring re-generation and re-compilation of C++
        code.

        *Examples of usage*

            .. code-block:: python

                p = Constant(pi/4)              # scalar
                C = Constant((0.0, -1.0, 0.0))  # constant vector

        """

        if cell is None:
            domain = None
        else:
            #deprecation_warning("The cell argument is no longer necessary.")
            domain = ufl.as_domain(cell)
            if not isinstance(domain, ufl.Domain):
                raise TypeError(
                    "Expected an ufl.Domain as the second argument")

        array = numpy.array(value)
        rank = len(array.shape)
        floats = list(map(float, array.flat))

        # Create UFL element and initialize constant
        if rank == 0:
            self._ufl_element = ufl.FiniteElement("Real", domain, 0)
            cpp.Constant.__init__(self, floats[0])
        elif rank == 1:
            self._ufl_element = ufl.VectorElement("Real", domain, 0,
                                                  len(floats))
            cpp.Constant.__init__(self, floats)
        else:
            self._ufl_element = ufl.TensorElement("Real",
                                                  domain,
                                                  0,
                                                  shape=array.shape)
            cpp.Constant.__init__(self, list(array.shape), floats)

        # Initialize base classes
        ufl.Coefficient.__init__(self, self._ufl_element, count=self.id())

        # Set name as given or automatic
        name = name or "f_%d" % self.count()
        self.rename(name, "a Constant")
Example #28
0
import time
import numba.core.typing.cffi_utils as cffi_support

import dolfiny.interpolation
import fecoda.misc
import ufl
import dolfinx
import dolfinx.io
from mpi4py import MPI
from cffi import FFI


N = 50
mesh = dolfinx.generation.UnitCubeMesh(MPI.COMM_WORLD, N, N, N)
deg = 0
V_el = ufl.TensorElement("DG", mesh.ufl_cell(), deg)
L_el = ufl.VectorElement("DG", mesh.ufl_cell(), deg, dim=3)
V = dolfinx.FunctionSpace(mesh, V_el)
L = dolfinx.FunctionSpace(mesh, L_el)

num_cells = mesh.topology.index_map(3).size_global
print(f"Num cells {num_cells}")

A = dolfinx.Function(V)
lam = dolfinx.Function(L)
lam_hand = dolfinx.Function(L)


def expr(x):
    values = numpy.zeros((9, x.shape[1]))
    values[0] = 1.0