COOLFluiD  Release kernel
COOLFluiD is a Collaborative Simulation Environment (CSE) focused on complex MultiPhysics simulations.
utest-mesh-interpolation.cpp
Go to the documentation of this file.
1 // Copyright (C) 2010-2013 von Karman Institute for Fluid Dynamics, Belgium
2 //
3 // This software is distributed under the terms of the
4 // GNU Lesser General Public License version 3 (LGPLv3).
5 // See doc/lgpl.txt and doc/gpl.txt for the license text.
6 
7 #define BOOST_TEST_DYN_LINK
8 #define BOOST_TEST_MODULE "Tests mesh interpolation"
9 
10 #include <boost/test/unit_test.hpp>
11 #include <boost/assign/list_of.hpp>
12 #include <boost/assign/std/vector.hpp>
13 
14 #include "common/Core.hpp"
15 #include "common/EventHandler.hpp"
16 #include "common/Environment.hpp"
17 #include "common/OptionArray.hpp"
18 #include "common/Foreach.hpp"
19 #include "common/Log.hpp"
20 #include "common/OptionList.hpp"
21 #include "common/Core.hpp"
22 #include "common/Table.hpp"
24 #include "common/Link.hpp"
26 
28 
29 #include "mesh/Mesh.hpp"
30 #include "mesh/Region.hpp"
31 #include "mesh/Elements.hpp"
32 #include "mesh/Dictionary.hpp"
34 #include "mesh/MeshReader.hpp"
35 #include "mesh/MeshWriter.hpp"
36 #include "mesh/Interpolator.hpp"
37 #include "mesh/Space.hpp"
38 #include "mesh/Connectivity.hpp"
39 #include "mesh/Field.hpp"
40 
42 
43 
44 using namespace boost;
45 using namespace boost::assign;
46 using namespace cf3;
47 using namespace cf3::mesh;
48 using namespace cf3::common;
49 
51 
53 {
56  {
57  // uncomment if you want to use arguments to the test executable
58  m_argc = boost::unit_test::framework::master_test_suite().argc;
59  m_argv = boost::unit_test::framework::master_test_suite().argv;
60 
61  }
62 
65  {
66  }
67 
69 
70  int m_argc;
71  char** m_argv;
72 };
73 
75 
76 BOOST_FIXTURE_TEST_SUITE( MeshInterpolation_TestSuite, MeshInterpolation_Fixture )
77 
78 
81 {
82  Core::instance().initiate(m_argc,m_argv);
83  PE::Comm::instance().init(m_argc,m_argv);
84  Core::instance().environment().options().set("log_level",(Uint)DEBUG);
85  Core::instance().environment().options().set("exception_backtrace",true);
86  Core::instance().environment().options().set("regist_signal_handlers",true);
87 }
88 
90 
91 BOOST_AUTO_TEST_CASE( Interpolation )
92 {
93  BOOST_CHECK( true );
94 
95  // create meshreader
96  boost::shared_ptr< MeshReader > meshreader = build_component_abstract_type<MeshReader>("cf3.mesh.neu.Reader","meshreader");
97 
98  BOOST_CHECK( true );
99 
100  Mesh& source = *Core::instance().root().create_component<Mesh>("box");
101 // meshreader->read_mesh_into("../../resources/hextet.neu",source);
102 
103  boost::shared_ptr<MeshGenerator> mesh_gen = allocate_component<SimpleMeshGenerator>("meshgen");
104  mesh_gen->options().set("nb_cells",std::vector<Uint>(3,5));
105  mesh_gen->options().set("lengths",std::vector<Real>(3,10.));
106  mesh_gen->options().set("mesh",source.uri());
107  mesh_gen->execute();
108 
109 
110  BOOST_CHECK_EQUAL( source.geometry_fields().coordinates().row_size() , (Uint)DIM_3D );
111 
112  Mesh& target = *Core::instance().root().create_component<Mesh>("quadtriag");
113  meshreader->read_mesh_into("../../resources/quadtriag.neu",target);
114 
115 #if 0
116 
117  BOOST_CHECK_EQUAL( target.geometry_fields().coordinates().row_size() , (Uint)DIM_2D );
118 
119  // boost::filesystem::path fp_target ("grid_c.cgns");
120 // boost::shared_ptr< MeshReader > cgns_meshreader = build_component_abstract_type<MeshReader>("cf3.mesh.CGNS.Reader","cgns_meshreader");
121 // Handle< Mesh > target = cgns_meshreader->create_mesh_from(fp_target);
122 
123 
124  // Create and configure interpolator.
125  boost::shared_ptr< Interpolator > interpolator = allocate_component<Interpolator>("interpolator");
126  interpolator->options().set("store",false);
127  BOOST_CHECK(true);
128 
129  std::string nvars = "rho_n[1] , V_n[3] , p_n[1]";
130  std::string nvars_2;
131  std::string evars;
132  std::string evars_2;
133 
134  nvars_2 = "rho_n_2[1] , V_n_2[3] , p_n_2[1]";
135  evars = "rho_e[1] , V_e[3] , p_e[1]";
136  evars_2 = "rho_e_2[1] , V_e_2[3] , p_e_2[1]";
137 
138  Dictionary& source_elem_fields = source.create_discontinuous_space("elems_P1", "cf3.mesh.LagrangeP1");
139  Dictionary& target_elem_fields = target.create_discontinuous_space("elems_P1", "cf3.mesh.LagrangeP1");
140  Dictionary& source_node_fields = source.geometry_fields();
141  Dictionary& target_node_fields = target.geometry_fields();
142 
143  // Create empty fields
144  Field& s_nodebased = source_node_fields.create_field( "nodebased", "rho_n[1], V_n[3], p_n[1]" );
145  Field& s_elembased = source_elem_fields.create_field( "elementbased", "rho_e[1], V_e[3], p_e[1]" );
146 
147  Field& t_nodebased = target_node_fields.create_field( "nodebased", "rho_n[1], V_n[3], p_n[1]" );
148  Field& t_nodebased_2 = target_node_fields.create_field( "nodebased_2", "rho_n_2[1], V_n_2[3], p_n_2[1]" );
149  Field& t_elembased = target_elem_fields.create_field( "elementbased", "rho_e[1], V_e[3], p_e[1]" );
150 
151  BOOST_CHECK(true);
152 
153  for ( Uint idx=0; idx!=s_nodebased.size(); ++idx)
154  {
155  Field::ConstRow coords = s_nodebased.coordinates()[idx];
156 
157  Field::Row data = s_nodebased[idx];
158 
159  data[0]=coords[XX]+2.*coords[YY]+2.*coords[ZZ];
160  data[1]=coords[XX];
161  data[2]=coords[YY];
162  data[3]=7.0;
163  data[4]=coords[XX];
164 
165  }
166 
167  boost_foreach( const Handle<Entities>& s_elements, s_elembased.entities_range() )
168  {
169  const Space& space = s_elembased.space(*s_elements);
170  const Field& coordinates = s_elembased.coordinates();
171  for (Uint elem_idx = 0; elem_idx<s_elements->size(); ++elem_idx)
172  {
173  boost_foreach(const Uint pt, space.connectivity()[elem_idx])
174  {
175  s_elembased[pt][0]=coordinates[pt][XX]+2.*coordinates[pt][YY]+2.*coordinates[pt][ZZ];
176  s_elembased[pt][1]=coordinates[pt][XX];
177  s_elembased[pt][2]=coordinates[pt][YY];
178  s_elembased[pt][3]=7.0;
179  s_elembased[pt][4]=coordinates[pt][XX];
180  }
181  }
182  }
183 
184 
185  BOOST_CHECK(true);
186 
187  // Interpolate the source field data to the target field. Note it can be in same or different meshes
188  BOOST_CHECK_NO_THROW(interpolator->interpolate(s_nodebased,s_elembased));
189  BOOST_CHECK_NO_THROW(interpolator->interpolate(s_nodebased,t_nodebased));
190  BOOST_CHECK_NO_THROW(interpolator->interpolate(s_elembased,t_nodebased_2));
191  BOOST_CHECK_NO_THROW(interpolator->interpolate(s_elembased,t_elembased));
192 
193  BOOST_CHECK(true);
194 
195  // Write the fields to file.
196  boost::shared_ptr< MeshWriter > meshwriter = build_component_abstract_type<MeshWriter>("cf3.mesh.gmsh.Writer","meshwriter");
197 
198  BOOST_CHECK(true);
199 
200  std::vector<URI> s_fields;
201  boost_foreach(Field& field, find_components_recursively<Field>(source))
202  s_fields.push_back(field.uri());
203 
204  meshwriter->options().set("fields",s_fields);
205  meshwriter->options().set("file",URI("source.msh"));
206  meshwriter->options().set("mesh",source.handle<Mesh>());
207  meshwriter->execute();
208 
209  std::vector<URI> t_fields;
210  boost_foreach(Field& field, find_components_recursively<Field>(target))
211  t_fields.push_back(field.uri());
212 
213  meshwriter->options().set("fields",t_fields);
214  meshwriter->options().set("file",URI("interpolated.msh"));
215  meshwriter->options().set("mesh",target.handle<Mesh>());
216  meshwriter->execute();
217  BOOST_CHECK(true);
218 
219 }
220 
222 
223 BOOST_AUTO_TEST_CASE( test_new_interpolation )
224 {
225  BOOST_CHECK( true );
226 
227  // Create mesh
228  boost::shared_ptr< MeshReader > meshreader = build_component_abstract_type<MeshReader>("cf3.mesh.neu.Reader","meshreader");
229  Handle<Mesh> source_mesh = Core::instance().root().create_component<Mesh>("hextet_new");
230 // meshreader->read_mesh_into("../../resources/hextet.neu",*source_mesh);
231  boost::shared_ptr<MeshGenerator> mesh_gen = allocate_component<SimpleMeshGenerator>("meshgen");
232  mesh_gen->options().set("nb_cells",std::vector<Uint>(3,5));
233  mesh_gen->options().set("lengths",std::vector<Real>(3,10.));
234  mesh_gen->options().set("mesh",source_mesh->uri());
235  mesh_gen->execute();
236 
237 
238  // Create and configure interpolator.
239  boost::shared_ptr< PointInterpolator > point_interpolator = allocate_component<PointInterpolator>("interpolator");
240 // interpolator->options().set("element_finder",std::string("cf3.mesh.Octtree"));
241 // interpolator->options().set("stencil_computer",std::string("cf3.mesh.StencilComputerOcttree"));
242 // interpolator->options().set("function",std::string("cf3.mesh.PseudoLaplacianLinearInterpolation"));
243 
244 
245  point_interpolator->options().set("dict",source_mesh->geometry_fields().handle<Dictionary>());
246 
247  RealVector coord(3); coord << 5., 1., 1.;
248  std::vector<Real> interpolated_value;
249  const Field& source_field = source_mesh->geometry_fields().coordinates();
250  point_interpolator->interpolate(source_field,coord,interpolated_value);
251  CFinfo << "interpolated value = " << to_str(interpolated_value) << CFendl;
252 
253  CFinfo << point_interpolator->info() << CFendl;
254 
255 
256  Dictionary& target_dict = source_mesh->create_continuous_space("target","cf3.mesh.LagrangeP1");
257  Field& target_field = target_dict.create_field("target","target[vector]");
258 
259  boost::shared_ptr< AInterpolator > interpolator = allocate_component<Interpolator>("interpolator");
260  interpolator->options().set("store",true);
261 
262  // first call: compute storage and store
263 
264  BOOST_CHECK_NO_THROW(interpolator->interpolate(source_mesh->geometry_fields().coordinates(),target_field));
265  CFinfo << target_field << CFendl;
266 
267  // second call: use stored values
268  BOOST_CHECK_NO_THROW(interpolator->interpolate(source_mesh->geometry_fields().coordinates(),target_field));
269  CFinfo << target_field << CFendl;
270 
271  // turn off storage, and compute again on the fly
272  interpolator->options().set("store",false);
273  BOOST_CHECK_NO_THROW(interpolator->interpolate(source_mesh->geometry_fields().coordinates(),target_field));
274  CFinfo << target_field << CFendl;
275 
276 
277  Handle<Mesh> source_mesh_2 = Core::instance().root().create_component<Mesh>("quadtriag_new");
278  meshreader->read_mesh_into("../../resources/quadtriag.neu",*source_mesh_2);
279 
280  Dictionary& target_dict_2 = source_mesh_2->create_continuous_space("target","cf3.mesh.LagrangeP2");
281  Field& target_field_2 = target_dict_2.create_field("target","target[vector]");
282 
283  interpolator->options().set("store",true);
284 
285  // first call: compute storage and store
286  BOOST_CHECK_NO_THROW(interpolator->interpolate(source_mesh_2->geometry_fields().coordinates(),target_field_2));
287  CFinfo << target_field_2 << CFendl;
288 
289  // second call: use stored values
290  BOOST_CHECK_NO_THROW(interpolator->interpolate(source_mesh_2->geometry_fields().coordinates(),target_field_2));
291  CFinfo << target_field_2 << CFendl;
292 
293  // turn off storage, and compute again on the fly
294  interpolator->options().set("store",false);
295  BOOST_CHECK_NO_THROW(interpolator->interpolate(source_mesh_2->geometry_fields().coordinates(),target_field_2));
296  CFinfo << target_field_2 << CFendl;
297 
298  target_field_2 = 0.;
299  std::vector<Uint> source_vars = boost::assign::list_of(0)(1);
300  std::vector<Uint> target_vars = boost::assign::list_of(1)(0);
301  BOOST_CHECK_NO_THROW(interpolator->interpolate_vars(source_mesh_2->geometry_fields().coordinates(),target_field_2,source_vars,target_vars));
302  CFinfo << target_field_2 << CFendl;
303 #endif
304 
305 }
306 
307 
309 
310 BOOST_AUTO_TEST_CASE( finalize_mpi )
311 {
312  PE::Comm::instance().finalize();
313 
314  Core::instance().terminate();
315 
316  // Check if any component pings back. No component should respond
317  XML::SignalFrame frame;
318  Core::instance().event_handler().raise_event("ping", frame);
319 
320 }
321 
323 
324 BOOST_AUTO_TEST_SUITE_END()
325 
326 
#define CFinfo
these are always defined
Definition: Log.hpp:104
Field & create_field(const std::string &name, const Uint cols)
Create a new field in this group.
Definition: Dictionary.cpp:178
Field & coordinates() const
Definition: Field.cpp:262
Safe pointer to an object. This is the supported method for referring to components.
Definition: Handle.hpp:39
Dictionary & create_discontinuous_space(const std::string &space_name, const std::string &space_lib_name, const std::vector< Handle< Entities > > &entities)
Definition: Mesh.cpp:316
external boost library namespace
MeshInterpolation_Fixture()
common setup for each test case
Dictionary & create_continuous_space(const std::string &space_name, const std::string &space_lib_name, const std::vector< Handle< Entities > > &entities)
Definition: Mesh.cpp:269
~MeshInterpolation_Fixture()
common tear-down for each test case
URI uri() const
Construct the full path.
Definition: Component.cpp:248
#define boost_foreach
lowercase version of BOOST_FOREACH
Definition: Foreach.hpp:16
const Field & coordinates() const
Definition: Dictionary.cpp:481
#define CFendl
Definition: Log.hpp:109
const std::vector< Handle< Entities > > & entities_range() const
Definition: Field.cpp:126
Definition: Defs.hpp:17
Common_API std::string to_str(const T &v)
Converts to std::string.
Handle< Component const > root() const
Definition: Component.cpp:266
Definition: Defs.hpp:17
Uint size() const
Definition: Table.hpp:127
Manages a set of maps.
Definition: SignalFrame.hpp:31
Uint size() const
return the number of elements
Definition: Entities.cpp:161
int m_argc
possibly common functions used on the tests below
Basic Classes for Mesh applications used by COOLFluiD.
Eigen::Matrix< Real, Eigen::Dynamic, 1 > RealVector
Dynamic sized column vector.
Definition: MatrixTypes.hpp:25
BOOST_AUTO_TEST_CASE(init_mpi)
const Handle< Space const > & space(const Handle< Entities const > &entities) const
Definition: Field.cpp:248
Top-level namespace for coolfluid.
Definition: Action.cpp:18
Uint row_size(Uint i=0) const
Definition: Table.hpp:133
boost::proto::terminal< SFOp< CoordinatesOp > >::type const coordinates
unsigned int Uint
typedef for unsigned int
Definition: CF.hpp:90
Handle< Component > handle()
Get a handle to the component.
Definition: Component.hpp:179
Definition: Defs.hpp:17
OptionList & options()
Definition: Component.cpp:856
Dictionary & geometry_fields() const
Definition: Mesh.cpp:339
Space component class.
Definition: Space.hpp:59
void set(const std::string &pname, const boost::any &val)
Definition: OptionList.cpp:132
Most basic kernel library.
Definition: Action.cpp:19
Connectivity & connectivity()
connectivity table to dictionary entries
Definition: Space.hpp:110
Send comments to:
COOLFluiD Web Admin