#pragma once #include #include #include #include #include #include #include #include namespace AMDiS { /// \brief The basic container that stores a base vector and a corresponding basis /** * A vector storing all the assembled Operators indexed with DOF indices. The vector * data is associated to a global basis. * * \tparam GB Basis of the vector * \tparam T Coefficient type to store in the vector * \tparam Traits Collection of parameter for the linear-algebra backend **/ template > class LinearForm : public VectorFacade { using Super = VectorFacade; using Self = LinearForm; public: /// The type of the functionspace basis associated to this linearform using GlobalBasis = GB; /// The type of the elements of the DOFVector using CoefficientType = T; /// The type of the vector filled on an element with local contributions using ElementVector = FlatVector; public: /// Constructor. Stores the shared_ptr of the basis and creates a new DataTransfer. explicit LinearForm(std::shared_ptr const& basis) : Super(*basis) , basis_(basis) { auto const localSize = basis->localView().maxSize(); elementVector_.resize(localSize); } /// Wraps the passed global basis into a (non-destroying) shared_ptr template )> explicit LinearForm(GB_&& basis) : LinearForm(Dune::wrap_or_move(FWD(basis))) {} GlobalBasis const& basis() const { return *basis_; } /// \brief Associate a local operator with this LinearForm /** * Stores an operator in a list that gets assembled during a call to \ref assemble(). * The operator may be assigned to a specific context, i.e. either an element * operator, an intersection operator, or a boundary operator. * The \p path tree paths specify the sub-basis for test functions the operator * is applied to. * * \tparam ContextTag One of \ref tag::element_operator, \ref tag::intersection_operator * or \ref tag::boundary_operator indicating where to assemble * this operator. * \tparam Expr An pre-operator that can be bound to a gridView, or a valid * GridOperator. * \tparam path A tree-path for the Basis * * [[expects: path is valid tree-path in Basis]] * @{ **/ template void addOperator(ContextTag contextTag, Expr const& expr, TreePath path); // Add an operator to be assembled on the elements of the grid template void addOperator(Expr const& expr, TreePath path = {}) { using E = typename GlobalBasis::LocalView::Element; addOperator(tag::element_operator{}, expr, path); } // Add an operator to be assembled on the intersections of the grid template void addIntersectionOperator(Expr const& expr, TreePath path = {}) { using I = typename GlobalBasis::LocalView::GridView::Intersection; addOperator(tag::intersection_operator{}, expr, path); } /// @} /// Assemble the vector operators on the bound element. template )> void assemble(LocalView const& localView); /// Assemble all vector operators added by \ref addOperator(). void assemble(); private: /// Dense vector to store coefficients during \ref assemble() ElementVector elementVector_; /// List of operators associated to nodes, filled in \ref addOperator(). VectorOperators operators_; std::shared_ptr basis_; }; // deduction guide template LinearForm(GB&& basis) -> LinearForm>; template auto makeLinearForm(GB&& basis) { using LF = LinearForm, T>; return LF{FWD(basis)}; } } // end namespace AMDiS #include