Commit a9ea8f7d by Pietro Incardona

### Improving the documentation of numeric

parent 90e8aaa8
 ... ... @@ -42,18 +42,28 @@ class Avg /*! \brief Calculate the position where the derivative is calculated * * In case on non staggered case this function just return pos, in case of staggered, * it calculate where the operator is calculated on a staggered grid * In case of non staggered case this function just return a null grid_key, in case of staggered, * it calculate how the operator shift the calculation in the cell * * \param position where we are calculating the derivative * \param gs Grid info * \param s_pos staggered position of the properties * */ inline static grid_key_dx position(grid_key_dx & pos, const grid_sm & gs) inline static grid_key_dx position(grid_key_dx & pos, const grid_sm & gs, const openfpm::vector> & s_pos = openfpm::vector>()) { std::cerr << "Error " << __FILE__ << ":" << __LINE__ << " only CENTRAL, FORWARD, BACKWARD derivative are defined"; } }; /*! \brief Average on direction i /*! \brief Central average scheme on direction i * * \verbatim * * +0.5 +0.5 * *---+---* * * \endverbatim * */ template ... ... @@ -61,8 +71,20 @@ class Avg { public: /*! \brief fill the row /*! \brief Calculate which colums of the Matrix are non zero * * stub_or_real it is just for change the argument type when testing, in normal * conditions it is a distributed map * * \param g_map It is the map explained in FDScheme * \param k_map position where the average is calculated * \param gs Grid info * \param cols non-zero colums calculated by the function * \param coeff coefficent (constant in front of the derivative) * * ### Example * * \snippet FDScheme_unit_tests.hpp Usage of stencil derivative * */ inline static void value(const typename stub_or_real::type & g_map, grid_dist_key_dx & kmap , const grid_sm & gs, typename Sys_eqs::stype (& spacing )[Sys_eqs::dims] , std::unordered_map & cols, typename Sys_eqs::stype coeff) ... ... @@ -87,43 +109,44 @@ class Avg } /*! \brief Calculate the position where the derivative is calculated /*! \brief Calculate the position where the average is calculated * * In case on non staggered case this function just return pos, in case of staggered, * it calculate where the operator is calculated on a staggered grid * It follow the same concept of central derivative * * \param pos from the position * \param fld Field we are deriving, if not provided the function just return pos * \param s_pos position of the properties in the staggered grid * \param position where we are calculating the derivative * \param gs Grid info * \param s_pos staggered position of the properties * */ inline static grid_key_dx position(grid_key_dx & pos, long int fld = -1, const openfpm::vector> & s_pos = openfpm::vector>()) inline static grid_key_dx position(grid_key_dx & pos, const grid_sm & gs, const comb (& s_pos)[Sys_eqs::nvar]) { auto arg_pos = arg::position(pos,gs,s_pos); if (is_grid_staggered::value()) { if (fld == -1) return pos; if (s_pos[fld][d] == 1) if (arg_pos.get(d) == -1) { grid_key_dx ret = pos; ret.set_d(d,0); return pos; arg_pos.set_d(d,0); return arg_pos; } else { grid_key_dx ret = pos; ret.set_d(d,1); return pos; arg_pos.set_d(d,-1); return arg_pos; } } return pos; return arg_pos; } }; /*! \brief Average FORWARD on direction i /*! \brief FORWARD average on direction i * * \verbatim * * +0.5 0.5 * +------* * * \endverbatim * */ template ... ... @@ -131,8 +154,20 @@ class Avg { public: /*! \brief fill the row /*! \brief Calculate which colums of the Matrix are non zero * * stub_or_real it is just for change the argument type when testing, in normal * conditions it is a distributed map * * \param g_map It is the map explained in FDScheme * \param k_map position where the average is calculated * \param gs Grid info * \param cols non-zero colums calculated by the function * \param coeff coefficent (constant in front of the derivative) * * ### Example * * \snippet FDScheme_unit_tests.hpp Usage of stencil derivative * */ inline static void value(const typename stub_or_real::type & g_map, grid_dist_key_dx & kmap , const grid_sm & gs, typename Sys_eqs::stype (& spacing )[Sys_eqs::dims] , std::unordered_map & cols, typename Sys_eqs::stype coeff) ... ... @@ -148,24 +183,30 @@ class Avg } /*! \brief Calculate the position where the derivative is calculated /*! \brief Calculate the position in the cell where the average is calculated * * In case on non staggered case this function just return pos, in case of staggered, * it calculate where the operator is calculated on a staggered grid * In case of non staggered case this function just return a null grid_key, in case of staggered, * the FORWARD scheme return the position of the staggered property * * \param pos from the position * \param fld Field we are deriving, if not provided the function just return pos * \param s_pos position of the properties in the staggered grid * \param position where we are calculating the derivative * \param gs Grid info * \param s_pos staggered position of the properties * */ inline static grid_key_dx position(grid_key_dx & pos, long int fld = -1, const openfpm::vector> & s_pos = openfpm::vector>()) inline static grid_key_dx position(grid_key_dx & pos, const grid_sm & gs, const comb (& s_pos)[Sys_eqs::nvar]) { return pos; return arg::position(pos,gs,s_pos); } }; /*! \brief Average BACKWARD on direction i /*! \brief First order BACKWARD derivative on direction i * * \verbatim * * +0.5 0.5 * *------+ * * \endverbatim * */ template ... ... @@ -173,8 +214,20 @@ class Avg { public: /*! \brief fill the row /*! \brief Calculate which colums of the Matrix are non zero * * stub_or_real it is just for change the argument type when testing, in normal * conditions it is a distributed map * * \param g_map It is the map explained in FDScheme * \param k_map position where the average is calculated * \param gs Grid info * \param cols non-zero colums calculated by the function * \param coeff coefficent (constant in front of the derivative) * * ### Example * * \snippet FDScheme_unit_tests.hpp Usage of stencil derivative * */ inline static void value(const typename stub_or_real::type & g_map, grid_dist_key_dx & kmap , const grid_sm & gs, typename Sys_eqs::stype (& spacing )[Sys_eqs::dims], std::unordered_map & cols, typename Sys_eqs::stype coeff) ... ... @@ -189,19 +242,19 @@ class Avg } /*! \brief Calculate the position where the derivative is calculated /*! \brief Calculate the position in the cell where the average is calculated * * In case on non staggered case this function just return pos, in case of staggered, * it calculate where the operator is calculated on a staggered grid * In case of non staggered case this function just return a null grid_key, in case of staggered, * the BACKWARD scheme return the position of the staggered property * * \param pos from the position * \param fld Field we are deriving, if not provided the function just return pos * \param s_pos position of the properties in the staggered grid * \param position where we are calculating the derivative * \param gs Grid info * \param s_pos staggered position of the properties * */ inline static grid_key_dx position(grid_key_dx & pos, long int fld = -1, const openfpm::vector> & s_pos = openfpm::vector>()) inline static grid_key_dx position(grid_key_dx & pos, const grid_sm & gs, const comb (& s_pos)[Sys_eqs::nvar]) { return pos; return arg::position(pos,gs,s_pos); } }; ... ...
This diff is collapsed.
 ... ... @@ -14,10 +14,11 @@ #include "eq.hpp" #include "data_type/scalar.hpp" #include "NN/CellList/CellDecomposer.hpp" #include "Grid/staggered_dist_grid_util.hpp" /*! \brief Finite Differences * * This class is able to discreatize on a Matrix any operator. In order to create a consistent * This class is able to discreatize on a Matrix any system of equations producing a linear system of type \f$Ax=B\f$. In order to create a consistent * Matrix it is required that each processor must contain a contiguos range on grid points without * holes. In order to ensure this, each processor produce a contiguos local labelling of its local * points. Each processor also add an offset equal to the number of local ... ... @@ -67,7 +68,53 @@ * * \endverbatim * * \tparam dim Dimensionality of the finite differences scheme * \tparam Sys_eqs Definition of the system of equations * * # Examples * * ## Solve lid-driven cavity 2D for incompressible fluid (inertia=0 --> Re=0) * * In this case the system of equation to solve is * * \f$\left\{ \begin{array}{c} \eta\nabla v_x + \partial_x P = 0 \quad Eq1 \\ \eta\nabla v_y + \partial_y P = 0 \quad Eq2 \\ \partial_x v_x + \partial_y v_y = 0 \quad Eq3 \end{array} \right. \f$ and boundary conditions * \f$\left\{ \begin{array}{c} v_x = 0, v_y = 0 \quad x = 0 \quad B1\\ v_x = 0, v_y = 1.0 \quad x = L \quad B2\\ v_x = 0, v_y = 0 \quad y = 0 \quad B3\\ v_x = 0, v_y = 0 \quad y = L \quad B4\\ \end{array} \right. \f$ * * with \f$v_x\f$ and \f$v_y\f$ the velocity in x and y and \f$P\f$ Pressure * * In order to solve such system first we define the general properties of the system * * \snippet eq_unit_test.hpp Definition of the system * * ## Define the equations of the system * * \snippet eq_unit_test.hpp Definition of the equation of the system in the bulk and at the boundary * * ## Define the domain and impose the equations * * \snippet eq_unit_test.hpp lid-driven cavity 2D * * # 3D * * A 3D case is given in the examples * */ ... ... @@ -111,12 +158,52 @@ private: // Grid points that has each processor openfpm::vector pnt; // Staggered position for each property comb s_pos[Sys_eqs::nvar]; // Each point in the grid has a global id, to decompose correctly the Matrix each processor contain a // contiguos range of global id, example processor 0 can have from 0 to 234 and processor 1 from 235 to 512 // no processors can have holes in the sequence, this number indicate where the sequence start for this // processor size_t s_pnt; struct key_and_eq { grid_key_dx key; size_t eq; }; /*! \brief From the row Matrix position to the spatial position * * \param row Matrix * * \return spatial position * */ inline key_and_eq from_row_to_key(size_t row) { key_and_eq ke; auto it = g_map.getDomainIterator(); while (it.isNext()) { size_t row_low = g_map.template get<0>(it.get()); if (row >= row_low * Sys_eqs::nvar && row < row_low * Sys_eqs::nvar + Sys_eqs::nvar) { ke.eq = row - row_low * Sys_eqs::nvar; ke.key = g_map.getGKey(it.get()); ke.key -= pd.getKP1(); return ke; } ++it; } std::cerr << "Error: " << __FILE__ << ":" << __LINE__ << " the row does not map to any position" << "\n"; return ke; } /* \brief calculate the mapping grid size with padding * * \param gs original grid size ... ... @@ -165,7 +252,10 @@ private: for (size_t i = 0 ; i < nz_rows.size() ; i++) { if (nz_rows.get(i) == false) std::cerr << "Error: " << __FILE__ << ":" << __LINE__ << " Ill posed matrix row " << i << " is not filled\n"; { key_and_eq ke = from_row_to_key(i); std::cerr << "Error: " << __FILE__ << ":" << __LINE__ << " Ill posed matrix row " << i << " is not filled, position " << ke.key.to_string() << " equation: " << ke.eq << "\n"; } } // all the colums must have a non zero element ... ... @@ -176,21 +266,42 @@ private: } } /* \brief Convert discrete ghost into continous ghost public: /*! \brief set the staggered position for each property * * \param Ghost * \param vector containing the staggered position for each property * */ inline Ghost convert_dg_cg(const Ghost & g) void setStagPos(comb (& sp)[Sys_eqs::nvar]) { return g_map_type::convert_ghost(g,g_map.getCellDecomposer()); for (size_t i = 0 ; i < Sys_eqs::nvar ; i++) s_pos[i] = sp[i]; } public: /*! \brief compute the staggered position for each property * * This is compute from the value_type stored by Sys_eqs::b_grid::value_type * * ### Example * * \snippet eq_unit_test.hpp Compute staggered properties * */ void computeStag() { typedef typename Sys_eqs::b_grid::value_type prp_type; /*! \brief Get the grid padding openfpm::vector> c_prp[prp_type::max_prop]; stag_set_position ssp(c_prp); boost::mpl::for_each_ref< boost::mpl::range_c >(ssp); } /*! \brief Get the specified padding * * \return the grid padding * \return the padding specified * */ const Padding & getPadding() ... ... @@ -199,6 +310,8 @@ public: } /*! \brief Return the map between the grid index position and the position in the distributed vector * * It is the map explained in the intro of the FDScheme * * \return the map * ... ... @@ -210,13 +323,17 @@ public: /*! \brief Constructor * * \param pd Padding * \param pd Padding, how many points out of boundary are present * \param domain extension of the domain * \param gs grid infos where Finite differences work * \param dec Decomposition of the domain * */ FDScheme(Padding & pd, const Box & domain, const grid_sm & gs, const typename Sys_eqs::b_grid::decomposition & dec, Vcluster & v_cl) FDScheme(Padding & pd, const Box & domain, const grid_sm & gs, const typename Sys_eqs::b_grid::decomposition & dec) :pd(pd),gs(gs),g_map(dec,padding(gs.getSize(),pd),domain,Ghost(1)),row(0),row_b(0) { Vcluster & v_cl = dec.getVC(); // Calculate the size of the local domain size_t sz = g_map.getLocalDomainSize(); ... ... @@ -337,17 +454,22 @@ public: for ( auto it = cols.begin(); it != cols.end(); ++it ) { trpl.add(); trpl.last().row() = Sys_eqs::nvar * gs.LinId(gkey) + id; trpl.last().row() = g_map.template get<0>(key)*Sys_eqs::nvar + id; trpl.last().col() = it->first; trpl.last().value() = it->second; std::cout << "(" << trpl.last().row() << "," << trpl.last().col() << "," << trpl.last().value() << ")" << "\n"; // std::cout << "(" << trpl.last().row() << "," << trpl.last().col() << "," << trpl.last().value() << ")" << "\n"; } b.get(Sys_eqs::nvar * gs.LinId(gkey) + id) = num; b.get(g_map.template get<0>(key)*Sys_eqs::nvar + id) = num; cols.clear(); std::cout << "\n"; // std::cout << "\n"; // if SE_CLASS1 is defined check the position #ifdef SE_CLASS1 T::position(gkey,gs,s_pos); #endif ++row; ++row_b; ... ... @@ -359,7 +481,7 @@ public: /*! \brief produce the Matrix * * \tparam Syst_eq System of equations, or a single equation * \return the Sparse matrix produced * */ typename Sys_eqs::SparseMatrix_type & getA() ... ... @@ -378,7 +500,7 @@ public: /*! \brief produce the B vector * * \tparam Syst_eq System of equations, or a single equation * \return the vector produced * */ typename Sys_eqs::Vector_type & getB() ... ...
 ... ... @@ -121,6 +121,8 @@ BOOST_AUTO_TEST_SUITE( fd_test ) BOOST_AUTO_TEST_CASE( der_central_non_periodic) { //! [Usage of stencil derivative] // grid size size_t sz[2]={16,16}; ... ... @@ -155,6 +157,8 @@ BOOST_AUTO_TEST_CASE( der_central_non_periodic) BOOST_REQUIRE_EQUAL(cols_y[17+16],1/spacing[1]/2.0); BOOST_REQUIRE_EQUAL(cols_y[17-16],-1/spacing[1]/2.0); //! [Usage of stencil derivative] // filled colums std::unordered_map cols_xx; ... ... @@ -178,19 +182,19 @@ BOOST_AUTO_TEST_CASE( der_central_non_periodic) BOOST_REQUIRE_EQUAL(cols_xx[34],-2/spacing[0]/spacing[0]/2.0/2.0); BOOST_REQUIRE_EQUAL(cols_xx[36],1/spacing[0]/spacing[0]/2.0/2.0); BOOST_REQUIRE_EQUAL(cols_xy[17],1/spacing[0]/spacing[1]); BOOST_REQUIRE_EQUAL(cols_xy[19],-1/spacing[0]/spacing[1]); BOOST_REQUIRE_EQUAL(cols_xy[49],-1/spacing[0]/spacing[1]); BOOST_REQUIRE_EQUAL(cols_xy[51],1/spacing[0]/spacing[1]); BOOST_REQUIRE_EQUAL(cols_xy[17],1/spacing[0]/spacing[1]/2.0/2.0); BOOST_REQUIRE_EQUAL(cols_xy[19],-1/spacing[0]/spacing[1]/2.0/2.0); BOOST_REQUIRE_EQUAL(cols_xy[49],-1/spacing[0]/spacing[1]/2.0/2.0); BOOST_REQUIRE_EQUAL(cols_xy[51],1/spacing[0]/spacing[1]/2.0/2.0); BOOST_REQUIRE_EQUAL(cols_yx[17],1/spacing[0]/spacing[1]); BOOST_REQUIRE_EQUAL(cols_yx[19],-1/spacing[0]/spacing[1]); BOOST_REQUIRE_EQUAL(cols_yx[49],-1/spacing[0]/spacing[1]); BOOST_REQUIRE_EQUAL(cols_xy[51],1/spacing[0]/spacing[1]); BOOST_REQUIRE_EQUAL(cols_yx[17],1/spacing[0]/spacing[1]/2.0/2.0); BOOST_REQUIRE_EQUAL(cols_yx[19],-1/spacing[0]/spacing[1]/2.0/2.0); BOOST_REQUIRE_EQUAL(cols_yx[49],-1/spacing[0]/spacing[1]/2.0/2.0); BOOST_REQUIRE_EQUAL(cols_xy[51],1/spacing[0]/spacing[1]/2.0/2.0); BOOST_REQUIRE_EQUAL(cols_yy[2],1/spacing[1]/spacing[1]); BOOST_REQUIRE_EQUAL(cols_yy[34],-2/spacing[1]/spacing[1]); BOOST_REQUIRE_EQUAL(cols_yy[66],1/spacing[1]/spacing[1]); BOOST_REQUIRE_EQUAL(cols_yy[2],1/spacing[1]/spacing[1]/2.0/2.0); BOOST_REQUIRE_EQUAL(cols_yy[34],-2/spacing[1]/spacing[1]/2.0/2.0); BOOST_REQUIRE_EQUAL(cols_yy[66],1/spacing[1]/spacing[1]/2.0/2.0); // Non periodic with one sided ... ... @@ -462,6 +466,8 @@ BOOST_AUTO_TEST_CASE( avg_central_staggered_non_periodic) BOOST_AUTO_TEST_CASE( lap_periodic) { //! [Laplacian usage] // grid size size_t sz[2]={16,16}; ... ... @@ -493,6 +499,8 @@ BOOST_AUTO_TEST_CASE( lap_periodic) BOOST_REQUIRE_EQUAL(cols[17],-2/spacing[0]/spacing[0] - 2/spacing[1]/spacing[1]); //! [Laplacian usage] cols.clear(); Lap,sys_pp>::value(g_map,key1414,ginfo,spacing,cols,1); ... ... @@ -512,6 +520,8 @@ BOOST_AUTO_TEST_CASE( lap_periodic) BOOST_AUTO_TEST_CASE( sum_periodic) { //! [sum example] // grid size size_t sz[2]={16,16}; ... ... @@ -538,6 +548,8 @@ BOOST_AUTO_TEST_CASE( sum_periodic) BOOST_REQUIRE_EQUAL(cols[17],2); //! [sum example] cols.clear(); sum, Field , Field ,sys_pp>::value(g_map,key11,ginfo,spacing,cols,1); ... ... @@ -548,11 +560,15 @@ BOOST_AUTO_TEST_CASE( sum_periodic) cols.clear(); //! [minus example] sum, Field , minus,sys_pp> ,sys_pp>::value(g_map,key11,ginfo,spacing,cols,1); BOOST_REQUIRE_EQUAL(cols.size(),1ul); BOOST_REQUIRE_EQUAL(cols[17],1ul); //! [minus example] } //////////////// Position //////////////////// ... ... @@ -560,73 +576,70 @@ BOOST_AUTO_TEST_CASE( sum_periodic) BOOST_AUTO_TEST_CASE( fd_test_use_staggered_position) { // grid size /* size_t sz[2]={16,16}; size_t sz[2]={16,16}; // grid_sm grid_sm<2,void> ginfo(sz); // Create a derivative row Matrix grid_key_dx<2> key11(1,1); grid_key_dx<2> key00(0,0); grid_key_dx<2> key11(1,1); grid_key_dx<2> key22(2,2); grid_key_dx<2> key1515(15,15); openfpm::vector> vx_c; comb<2> cx = {{1,0}}; vx_c.add(cx); // like v_x openfpm::vector> vy_c; comb<2> cy = {{0,1}}; vy_c.add(cy); // like v_y grid_key_dx<2> key_ret_x = D,sys_nn>::position(key11,0,vx_c); grid_key_dx<2> key_ret_y = D,sys_nn>::position(key11,0,vx_c); BOOST_REQUIRE_EQUAL(key_ret_x.get(0),1); BOOST_REQUIRE_EQUAL(key_ret_x.get(1),1); BOOST_REQUIRE_EQUAL(key_ret_y.get(0),0); BOOST_REQUIRE_EQUAL(key_ret_y.get(1),0); comb<2> vx_c[] = {{0,-1}}; comb<2> vy_c[] = {{-1,0}}; key_ret_x = D,sys_nn>::position(key11,0,vy_c); key_ret_y = D,sys_nn>::position(key11,0,vy_c); grid_key_dx<2> key_ret_vx_x = D,syss_nn>::position(key00,ginfo,vx_c); grid_key_dx<2> key_ret_vx_y = D,syss_nn>::position(key00,ginfo,vx_c); grid_key_dx<2> key_ret_vy_x = D,syss_nn>::position(key00,ginfo,vy_c); grid_key_dx<2> key_ret_vy_y = D,syss_nn>::position(key00,ginfo,vy_c); BOOST_REQUIRE_EQUAL(key_ret_x.get(0),0);