### 1. Interpolation

Feel++ has a very powerful interpolation framework which allows to:

• transfer functions from one mesh to another

• transfer functions from one space type to another.

this is done seamlessly in parallel. The framework provides a set of C++ classes and C++ free-functions enabled short, concise and expressive handling of interpolation.

#### 1.1. Using interpolation operator

Building interpolation operator $I_h : P^1_{c,h} \rightarrow P^0_{td.h}$
``````using MeshType = Mesh<Simplex<2>>;
auto mesh = loadMesh( _mesh=new MeshType );
auto P1h = Pch<1>( mesh );
auto P0h = Pdh<0>( mesh );
auto Ih = I( _domain=P1h, _image=P0h );``````

#### 1.2. De Rahm Diagram

The De Rahm diagram reads as follows: the range of each of the operators coincides with the null space of the next operator in the sequence below, and the last map is a surjection.

$\begin{array}{ccccccc} H^1(\Omega)& \overset{\nabla}{\longrightarrow}& H^{\mathrm{curl}}(\Omega)& \overset{\nabla \times}{\longrightarrow}& H^{\mathrm{div}}(\Omega)& \overset{\nabla \cdot}{\longrightarrow}& L^2(\Omega) \end{array}$

An important result is that the diagram transfers to the discrete level

$\begin{array}{ccccccc} H^1(\Omega)& \overset{\nabla}{\longrightarrow}& H^{\mathrm{curl}}(\Omega)& \overset{\nabla \times}{\longrightarrow}& H^{\mathrm{div}}(\Omega)& \overset{\nabla \cdot}{\longrightarrow}& L^2(\Omega) \\ \left\downarrow\right.\pi_{c,h}& ~ & \left\downarrow\right.\pi_{\mathrm{curl},h}& ~ & \left\downarrow\right.\pi_{\mathrm{div},_h}& ~ & \left\downarrow\right.\pi_{d,h}& ~ \\ U_h& \overset{\nabla}{\longrightarrow}& V_h& \overset{\nabla \times}{\longrightarrow}& W_h& \overset{\nabla \cdot}{\longrightarrow}& Z_h\\ \end{array}$

The diagram above is commutative which means that we have the following properties:

\begin{aligned} \nabla(\pi_{c,h} u) &= \pi_{\mathrm{curl},h}( \nabla u ),\\ \nabla\times(\pi_{\mathrm{curl},h} u) &= \pi_{\mathrm{div},h}( \nabla\times u ),\\ \nabla\cdot(\pi_{\mathrm{div},h} u) &= \pi_{d,h}( \nabla\cdot u ) \end{aligned}
 The diagram can be restricted to functions satisfying the homogeneous Dirichlet boundary conditions
$\begin{array}{ccccccc} H^1_0(\Omega)& \overset{\nabla}{\longrightarrow}& H_0^{\mathrm{curl}}(\Omega)& \overset{\nabla \times}{\longrightarrow}& H_0^{\mathrm{div}}(\Omega)& \overset{\nabla \cdot}{\longrightarrow}& L^2_0(\Omega) \end{array}$

Interpolation operators are provided as is or as shared pointers. The table below presents the alternatives.

 C++ object C++ Type C++ shared object C++ Type Mathematical operator `I(_domain=Xh,_image=Yh)` ```I_t, functionspace_type>``` `IPtr(…​)` ```I_ptr_t, functionspace_type>``` $I: X_h \rightarrow Y_h$ `Grad(_domain=Xh,_image=Wh)` ```Grad_t, functionspace_type>``` `GradPtr(…​)` ```Grad_ptr_t, functionspace_type>``` $\nabla: X_h \rightarrow W_h$ `Curl(_domain=Wh,_image=Vh)` ```Curl_t, functionspace_type>``` `CurlPtr(…​)` ```Curl_ptr_t, functionspace_type>``` $\nabla \times : W_h \rightarrow V_h$ `Div(_domain=Vh,_image=Zh)` ```Div_t, functionspace_type>``` `DivPtr(…​)` ```Div_ptr_t, functionspace_type>``` $\nabla \cdot: V_h \rightarrow Z_h$
Building the discrete operators associated to the De Rahm diagram in Feel++
``````auto mesh = loadMesh( _mesh=new Mesh<Simplex<Dim>>());
auto Xh = Pch<1>(mesh);
auto Gh = Ned1h<0>(mesh);
auto Ch = Dh<0>(mesh);
auto P0h = Pdh<0>(mesh);