source: src/Fragmentation/Summation/SetValues/unittests/SamplingGridUnitTest.cpp@ 91e7658

Action_Thermostats Add_AtomRandomPerturbation Add_FitFragmentPartialChargesAction Add_RotateAroundBondAction Add_SelectAtomByNameAction Adding_Graph_to_ChangeBondActions Adding_MD_integration_tests Adding_StructOpt_integration_tests Automaking_mpqc_open AutomationFragmentation_failures Candidate_v1.5.4 Candidate_v1.6.0 Candidate_v1.6.1 ChangeBugEmailaddress ChangingTestPorts ChemicalSpaceEvaluator Combining_Subpackages Debian_Package_split Debian_package_split_molecuildergui_only Disabling_MemDebug Docu_Python_wait EmpiricalPotential_contain_HomologyGraph EmpiricalPotential_contain_HomologyGraph_documentation Enable_parallel_make_install Enhance_userguide Enhanced_StructuralOptimization Enhanced_StructuralOptimization_continued Example_ManyWaysToTranslateAtom Exclude_Hydrogens_annealWithBondGraph FitPartialCharges_GlobalError Fix_ChargeSampling_PBC Fix_ChronosMutex Fix_FitPartialCharges Fix_FitPotential_needs_atomicnumbers Fix_ForceAnnealing Fix_IndependentFragmentGrids Fix_ParseParticles Fix_ParseParticles_split_forward_backward_Actions Fix_StatusMsg Fix_StepWorldTime_single_argument Fix_Verbose_Codepatterns ForceAnnealing_goodresults ForceAnnealing_oldresults ForceAnnealing_tocheck ForceAnnealing_with_BondGraph ForceAnnealing_with_BondGraph_continued ForceAnnealing_with_BondGraph_continued_betteresults ForceAnnealing_with_BondGraph_contraction-expansion GeometryObjects Gui_displays_atomic_force_velocity IndependentFragmentGrids IndependentFragmentGrids_IndividualZeroInstances IndependentFragmentGrids_IntegrationTest IndependentFragmentGrids_Sole_NN_Calculation JobMarket_RobustOnKillsSegFaults JobMarket_StableWorkerPool JobMarket_unresolvable_hostname_fix ODR_violation_mpqc_open PartialCharges_OrthogonalSummation PythonUI_with_named_parameters QtGui_reactivate_TimeChanged_changes Recreated_GuiChecks RotateToPrincipalAxisSystem_UndoRedo StoppableMakroAction Subpackage_CodePatterns Subpackage_JobMarket Subpackage_LinearAlgebra Subpackage_levmar Subpackage_mpqc_open Subpackage_vmg ThirdParty_MPQC_rebuilt_buildsystem TrajectoryDependenant_MaxOrder TremoloParser_IncreasedPrecision TremoloParser_MultipleTimesteps Ubuntu_1604_changes stable
Last change on this file since 91e7658 was 91e7658, checked in by Frederik Heber <heber@…>, 8 years ago

SamplingGridUnitTest checks downsample on window.

  • FIX: getLengthsOfGrid() asserted that total equals 2level which is only true if the window spans the whole grid. We now assert for equal or less.
  • Renamed getLengthsOfGrid -> getLengthsOfWindow.
  • Extended downsample() tests to check for level difference of one to three.
  • Property mode set to 100644
File size: 30.9 KB
Line 
1/*
2 * Project: MoleCuilder
3 * Description: creates and alters molecular systems
4 * Copyright (C) 2012 University of Bonn. All rights reserved.
5 * Copyright (C) 2013 Frederik Heber. All rights reserved.
6 *
7 *
8 * This file is part of MoleCuilder.
9 *
10 * MoleCuilder is free software: you can redistribute it and/or modify
11 * it under the terms of the GNU General Public License as published by
12 * the Free Software Foundation, either version 2 of the License, or
13 * (at your option) any later version.
14 *
15 * MoleCuilder is distributed in the hope that it will be useful,
16 * but WITHOUT ANY WARRANTY; without even the implied warranty of
17 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
18 * GNU General Public License for more details.
19 *
20 * You should have received a copy of the GNU General Public License
21 * along with MoleCuilder. If not, see <http://www.gnu.org/licenses/>.
22 */
23
24/*
25 * SamplingGridUnitTest.cpp
26 *
27 * Created on: Jul 29, 2012
28 * Author: heber
29 */
30
31// include config.h
32#ifdef HAVE_CONFIG_H
33#include <config.h>
34#endif
35
36using namespace std;
37
38#include <cppunit/CompilerOutputter.h>
39#include <cppunit/extensions/TestFactoryRegistry.h>
40#include <cppunit/ui/text/TestRunner.h>
41
42// include headers that implement a archive in simple text format
43#include <boost/archive/text_oarchive.hpp>
44#include <boost/archive/text_iarchive.hpp>
45
46#include "SamplingGridUnitTest.hpp"
47
48#include "CodePatterns/Assert.hpp"
49#include "CodePatterns/Log.hpp"
50
51#include <boost/assign.hpp>
52
53#include <cmath>
54#include <numeric>
55
56#ifdef HAVE_TESTRUNNER
57#include "UnitTestMain.hpp"
58#endif /*HAVE_TESTRUNNER*/
59
60using namespace boost::assign;
61
62/********************************************** Test classes **************************************/
63
64const double grid_value=1.;
65
66#define NUMBEROFSAMPLES(n) (size_t)(pow(pow(2,n),(int)NDIM))
67#define DOMAINVOLUME(l) (size_t)pow(l,(int)NDIM)
68
69// Registers the fixture into the 'registry'
70CPPUNIT_TEST_SUITE_REGISTRATION( SamplingGridTest );
71
72
73void SamplingGridTest::setUp()
74{
75 // failing asserts should be thrown
76 ASSERT_DO(Assert::Throw);
77
78 // create the grid
79 const double begin[NDIM] = { 0., 0., 0. };
80 const double end[NDIM] = { 1., 1., 1. };
81 for (size_t i=0; i< DOMAINVOLUME(1)*NUMBEROFSAMPLES(2); ++i)
82 values += grid_value;
83 grid = new SamplingGrid(begin, end, 2, values);
84 CPPUNIT_ASSERT_EQUAL( grid_value, *(grid->sampled_grid.begin()) );
85}
86
87
88void SamplingGridTest::tearDown()
89{
90 delete grid;
91}
92
93/** UnitTest on equivalent combination of props and values
94 */
95void SamplingGridTest::equivalentGrids_Test()
96{
97 // check illegal grid
98 const double begin[NDIM] = { 0., 0., 0. };
99 const double end[NDIM] = { 1., 1., 1. };
100 SamplingGridProperties illegal_props(begin, end, 5);
101 SamplingGridProperties legal_props(begin, end, 2);
102 CPPUNIT_ASSERT( !grid->isEquivalent(illegal_props) );
103 CPPUNIT_ASSERT( grid->isEquivalent(legal_props) );
104 SamplingGrid::sampledvalues_t illegal_values;
105 for (size_t i=0; i< NUMBEROFSAMPLES(1); ++i)
106 illegal_values += 1.5;
107 SamplingGrid::sampledvalues_t legal_values;
108 for (size_t i=0; i< NUMBEROFSAMPLES(2); ++i)
109 legal_values += 1.5;
110#ifndef NDEBUG
111 // throws because props and size of illegal_values don't match
112 std::cout << "The following assertion is intended and does not indicate a failure of the test." << std::endl;
113 CPPUNIT_ASSERT_THROW( SamplingGrid illegal_grid(illegal_props, illegal_values), Assert::AssertionFailure );
114 std::cout << "The following assertion is intended and does not indicate a failure of the test." << std::endl;
115 CPPUNIT_ASSERT_THROW( SamplingGrid illegal_grid(legal_props, illegal_values), Assert::AssertionFailure );
116 std::cout << "The following assertion is intended and does not indicate a failure of the test." << std::endl;
117 CPPUNIT_ASSERT_THROW( SamplingGrid illegal_grid(illegal_props, legal_values), Assert::AssertionFailure );
118#endif
119 // check that grid is still the same
120 for (SamplingGrid::sampledvalues_t::const_iterator iter = grid->sampled_grid.begin();
121 iter != grid->sampled_grid.end(); ++iter)
122 CPPUNIT_ASSERT_EQUAL( grid_value, *iter );
123}
124
125/** UnitTest on compatible combination of props and values
126 */
127void SamplingGridTest::compatibleGrids_Test()
128{
129 // check illegal grid
130 const double begin[NDIM] = { 0., 0., 0. };
131 const double end[NDIM] = { 1., 1., 1. };
132 const double otherend[NDIM] = { 2.5, 2.5, 2.5 };
133 SamplingGridProperties illegal_props(begin, otherend, 5);
134 SamplingGridProperties legal_props(begin, end, 3);
135 CPPUNIT_ASSERT( !grid->isCompatible(illegal_props) );
136 CPPUNIT_ASSERT( grid->isCompatible(legal_props) );
137 SamplingGrid::sampledvalues_t illegal_values;
138 for (size_t i=0; i< NUMBEROFSAMPLES(1); ++i)
139 illegal_values += 1.5;
140 SamplingGrid::sampledvalues_t legal_values;
141 for (size_t i=0; i< NUMBEROFSAMPLES(2); ++i)
142 legal_values += 1.5;
143#ifndef NDEBUG
144 // throws because props and size of illegal_values don't match
145 std::cout << "The following assertion is intended and does not indicate a failure of the test." << std::endl;
146 CPPUNIT_ASSERT_THROW( SamplingGrid illegal_grid(illegal_props, illegal_values), Assert::AssertionFailure );
147 std::cout << "The following assertion is intended and does not indicate a failure of the test." << std::endl;
148 CPPUNIT_ASSERT_THROW( SamplingGrid illegal_grid(legal_props, illegal_values), Assert::AssertionFailure );
149 std::cout << "The following assertion is intended and does not indicate a failure of the test." << std::endl;
150 CPPUNIT_ASSERT_THROW( SamplingGrid illegal_grid(illegal_props, legal_values), Assert::AssertionFailure );
151#endif
152 // check that grid is still the same
153 for (SamplingGrid::sampledvalues_t::const_iterator iter = grid->sampled_grid.begin();
154 iter != grid->sampled_grid.end(); ++iter)
155 CPPUNIT_ASSERT_EQUAL( grid_value, *iter );
156}
157
158/** UnitTest for isCongruent()
159 */
160void SamplingGridTest::isCongruent_Test()
161{
162 const double begin[NDIM] = { 0., 0., 0. };
163 const double end[NDIM] = { 2., 2., 2. };
164 const double otherbegin[NDIM] = { 0.1, 0.1, 0.1 };
165 const double otherend[NDIM] = { 1., 1., 1. };
166 SamplingGridProperties illegal_begin_props(otherbegin, end, 5);
167 SamplingGridProperties illegal_end_props(begin, otherend, 5);
168 SamplingGridProperties illegal_level_props(begin, end, 5);
169 SamplingGridProperties legal_props(begin, end, 2);
170
171 // differing windows
172// const double begin_window[NDIM] = { 0.5, 0.5, 0.5 };
173// const double end_window[NDIM] = { 1., 1., 1. };
174 const double otherbegin_window[NDIM] = { 0.45, 0.45, 0.45 };
175 const double otherend_window[NDIM] = { 1.05, 1.05, 1.05 };
176
177 // check that incompatible grid are also incongruent
178 SamplingGrid default_grid(legal_props);
179 // note that we always construct a temporary SamplingGrid from given props
180 CPPUNIT_ASSERT( default_grid.isEquivalent(illegal_begin_props) == default_grid.isCongruent(illegal_begin_props));
181 CPPUNIT_ASSERT( default_grid.isEquivalent(illegal_end_props) == default_grid.isCongruent(illegal_end_props));
182 CPPUNIT_ASSERT( default_grid.isEquivalent(illegal_level_props) == default_grid.isCongruent(illegal_level_props));
183 CPPUNIT_ASSERT( default_grid.isEquivalent(legal_props) == default_grid.isCongruent(legal_props) );
184
185 default_grid.setWindowSize(begin, end);
186 // same window
187 {
188 SamplingGrid illegal_begin_grid(illegal_begin_props);
189 SamplingGrid illegal_end_grid(illegal_end_props);
190 SamplingGrid illegal_level_grid(illegal_level_props);
191 SamplingGrid legal_grid(legal_props);
192 illegal_begin_grid.setWindowSize(begin, end);
193 illegal_end_grid.setWindowSize(begin, end);
194 illegal_level_grid.setWindowSize(begin, end);
195 legal_grid.setWindowSize(begin, end);
196 CPPUNIT_ASSERT( !illegal_begin_grid.isCongruent(default_grid) );
197 CPPUNIT_ASSERT( !illegal_end_grid.isCongruent(default_grid) );
198 CPPUNIT_ASSERT( !illegal_level_grid.isCongruent(default_grid) );
199 CPPUNIT_ASSERT( legal_grid.isCongruent(default_grid) );
200 }
201
202 // different begin
203 {
204 SamplingGrid illegal_begin_grid(illegal_begin_props);
205 SamplingGrid illegal_end_grid(illegal_end_props);
206 SamplingGrid illegal_level_grid(illegal_level_props);
207 SamplingGrid legal_grid(legal_props);
208 illegal_begin_grid.setWindowSize(otherbegin_window, end);
209 illegal_end_grid.setWindowSize(otherbegin_window, end);
210 illegal_level_grid.setWindowSize(otherbegin_window, end);
211 legal_grid.setWindowSize(begin, end);
212 CPPUNIT_ASSERT( !illegal_begin_grid.isCongruent(legal_grid) );
213 CPPUNIT_ASSERT( !illegal_end_grid.isCongruent(legal_grid) );
214 CPPUNIT_ASSERT( !illegal_level_grid.isCongruent(legal_grid) );
215 CPPUNIT_ASSERT( legal_grid.isCongruent(default_grid) );
216 }
217
218 // different end
219 {
220 SamplingGrid illegal_begin_grid(illegal_begin_props);
221 SamplingGrid illegal_end_grid(illegal_end_props);
222 SamplingGrid illegal_level_grid(illegal_level_props);
223 SamplingGrid legal_grid(legal_props);
224 illegal_begin_grid.setWindowSize(begin, otherend_window);
225 illegal_end_grid.setWindowSize(begin, otherend_window);
226 illegal_level_grid.setWindowSize(begin, otherend_window);
227 legal_grid.setWindowSize(begin, end);
228 CPPUNIT_ASSERT( !illegal_begin_grid.isCongruent(legal_grid) );
229 CPPUNIT_ASSERT( !illegal_end_grid.isCongruent(legal_grid) );
230 CPPUNIT_ASSERT( !illegal_level_grid.isCongruent(legal_grid) );
231 CPPUNIT_ASSERT( legal_grid.isCongruent(default_grid) );
232 }
233
234 // different begin and end
235 {
236 SamplingGrid illegal_begin_grid(illegal_begin_props);
237 SamplingGrid illegal_end_grid(illegal_end_props);
238 SamplingGrid illegal_level_grid(illegal_level_props);
239 SamplingGrid legal_grid(legal_props);
240 illegal_begin_grid.setWindowSize(otherbegin_window, otherend_window);
241 illegal_end_grid.setWindowSize(otherbegin_window, otherend_window);
242 illegal_level_grid.setWindowSize(otherbegin_window, otherend_window);
243 legal_grid.setWindowSize(begin, end);
244 CPPUNIT_ASSERT( !illegal_begin_grid.isCongruent(legal_grid) );
245 CPPUNIT_ASSERT( !illegal_end_grid.isCongruent(legal_grid) );
246 CPPUNIT_ASSERT( !illegal_level_grid.isCongruent(legal_grid) );
247 CPPUNIT_ASSERT( legal_grid.isCongruent(default_grid) );
248 }
249}
250
251/** UnitTest for integral()
252 */
253void SamplingGridTest::integral_Test()
254{
255 double sum = 0.;
256 sum = std::accumulate( grid->sampled_grid.begin(), grid->sampled_grid.end(), sum );
257 CPPUNIT_ASSERT_EQUAL( sum*grid->getVolume()/grid->getWindowGridPoints(), grid->integral() );
258}
259
260/** UnitTest for getVolume()
261 */
262void SamplingGridTest::getVolume_Test()
263{
264 CPPUNIT_ASSERT_EQUAL( 1., grid->getVolume() );
265}
266
267/** UnitTest for getWindowSize()
268 */
269void SamplingGridTest::getWindowSize_Test()
270{
271 // check size of default grid
272 CPPUNIT_ASSERT_EQUAL( (size_t)(NUMBEROFSAMPLES(grid->level)), grid->getWindowGridPoints() );
273
274 // create another one and check its size, too
275 const double begin[NDIM] = { 0., 0., 0. };
276 const double end[NDIM] = { 1., 1., 1. };
277 for (size_t level = 3; level<=6; ++level) {
278 values.clear();
279 for (size_t i=0; i< NUMBEROFSAMPLES(level); ++i)
280 values += grid_value;
281 delete grid;
282 // use other pointer in case something fails
283 SamplingGrid *tmpgrid = new SamplingGrid(begin, end, level, values);
284 grid = tmpgrid;
285 CPPUNIT_ASSERT_EQUAL( (size_t)NUMBEROFSAMPLES(level), grid->getWindowGridPoints() );
286 }
287}
288
289/** UnitTest for extendWindow()
290 */
291void SamplingGridTest::extendWindow_Test()
292{
293 // we have a grid with size of one, extend to twice the size and check
294 const double begin[NDIM] = { 0., 0., 0. };
295 const double size = 2.;
296 const double end[NDIM] = { size, size, size };
297 double offset[NDIM];
298 for (offset[0] = 0.; offset[0] <= 1.; offset[0] += .5)
299 for (offset[1] = 0.; offset[1] <= 1.; offset[1] += .5)
300 for (offset[2] = 0.; offset[2] <= 1.; offset[2] += .5) {
301 const double window_begin[NDIM] = { 0.+offset[0], 0.+offset[1], 0.+offset[2]};
302 const double window_end[NDIM] = { 1.+offset[0], 1.+offset[1], 1.+offset[2]};
303 SamplingGrid newgrid(begin, end, 2);
304 newgrid.setWindowSize(window_begin, window_end);
305 // resize values by hand to new window size. Otherwise they get zero'd.
306 newgrid.sampled_grid = values;
307 newgrid.sampled_grid.resize(NUMBEROFSAMPLES(1));
308 newgrid.extendWindow(begin, end);
309
310 // check integral
311 CPPUNIT_ASSERT_EQUAL(
312 grid_value/(NUMBEROFSAMPLES(grid->level)/NUMBEROFSAMPLES(grid->level)),
313 grid->integral()
314 );
315
316 // check number of points
317 CPPUNIT_ASSERT_EQUAL(
318 (size_t)NUMBEROFSAMPLES(grid->level),
319 grid->getWindowGridPoints()
320 );
321 }
322}
323
324/** UnitTest for extendWindow() with asymmetric values
325 */
326void SamplingGridTest::extendWindow_asymmetric_Test()
327{
328 std::cout << "SamplingGridTest::extendWindow_asymmetric_Test()" << std::endl;
329 const double begin[NDIM] = { 0., 0., 0. };
330 const double end[NDIM] = { 2., 2., 2. };
331 double offset[NDIM];
332 for (offset[0] = 0.; offset[0] <= 1.; offset[0] += .5)
333 for (offset[1] = 0.; offset[1] <= 1.; offset[1] += .5)
334 for (offset[2] = 0.; offset[2] <= 1.; offset[2] += .5) {
335 const double window_begin[NDIM] = { 0.+offset[0], 0.+offset[1], 0.+offset[2]};
336 const double window_end[NDIM] = { 1.+offset[0], 1.+offset[1], 1.+offset[2]};
337 SamplingGrid newgrid(begin, end, 2);
338 CPPUNIT_ASSERT_EQUAL( (size_t)0, newgrid.getWindowGridPoints() );
339 newgrid.setWindowSize(window_begin, window_end);
340 // window size is only half of domain size
341 const size_t max_samples = NUMBEROFSAMPLES(newgrid.level)*pow(0.5,(int)NDIM);
342 for (size_t i=0; i< max_samples; ++i)
343 newgrid.sampled_grid += grid_value*i;
344 const size_t sum_weight = (max_samples)*(max_samples-1)/2;
345 const double integral = newgrid.integral();
346 newgrid.extendWindow(begin, end);
347
348 // check that integral has remained the same
349 CPPUNIT_ASSERT_EQUAL( integral, newgrid.integral() );
350 CPPUNIT_ASSERT_EQUAL( grid_value*sum_weight/DOMAINVOLUME(2), newgrid.integral() );
351 }
352}
353
354/** UnitTest for addOntoWindow()
355 */
356void SamplingGridTest::addOntoWindow_Test()
357{
358 // first window is from (0,0,0) to (1,1,1)
359 CPPUNIT_ASSERT_EQUAL( 1.*grid_value, grid->integral() );
360
361 // create values for half-sized window
362 values.clear();
363 for (size_t i=0; i< (size_t)pow(.5*pow(2,2),(int)NDIM); ++i)
364 values += grid_value;
365
366 // check that too large a window throws
367#ifndef NDEBUG
368 const double begin[NDIM] = { .5, .5, .5 };
369 const double wrongend[NDIM] = { 1.5, 1.5, 1.5 };
370 std::cout << "The following assertion is intended and does not indicate a failure of the test." << std::endl;
371 CPPUNIT_ASSERT_THROW( grid->addOntoWindow(begin, wrongend, values, +1.), Assert::AssertionFailure );
372#endif
373
374 // create another window from (.5,.5,.5) to (1., 1., 1.)
375 double offset[NDIM];
376 for (offset[0] = 0.; offset[0] <= .5; offset[0] += .5)
377 for (offset[1] = 0.; offset[1] <= .5; offset[1] += .5)
378 for (offset[2] = 0.; offset[2] <= .5; offset[2] += .5) {
379 const double window_begin[NDIM] = { 0.+offset[0], 0.+offset[1], 0.+offset[2]};
380 const double window_end[NDIM] = { .5+offset[0], .5+offset[1], .5+offset[2]};
381
382 SamplingGrid newgrid(*grid);
383 // now perform working operation
384 newgrid.addOntoWindow(window_begin, window_end, values, +1.);
385
386 // check integral to be one and one eighth times the old value
387 CPPUNIT_ASSERT_EQUAL( (1.+pow(.5,(int)NDIM))*grid_value, newgrid.integral() );
388 }
389}
390
391/** UnitTest for addOntoWindow() with asymmetric values
392 */
393void SamplingGridTest::addOntoWindow_asymmetric_Test()
394{
395 const size_t size = grid->end[0]-grid->begin[0];
396 // check with asymmetric values
397 grid->sampled_grid.clear();
398 grid->sampled_grid.resize(DOMAINVOLUME(size)*NUMBEROFSAMPLES(grid->level), 0.);
399
400 for (size_t i=0;i<grid->level*(grid->end[0]-grid->begin[0]);++i)
401 grid->sampled_grid[(i*2+0)*2+0] += .5*grid_value;
402 for (size_t i=0;i<grid->level*(grid->end[1]-grid->begin[1]);++i)
403 grid->sampled_grid[(0*2+i)*2+0] += 1.*grid_value;
404 for (size_t i=0;i<grid->level*(grid->end[2]-grid->begin[2]);++i)
405 grid->sampled_grid[(0*2+0)*2+i] += 1.5*grid_value;
406
407 const double integral = grid->integral();
408
409 // now perform working operation
410 grid->addOntoWindow(grid->begin, grid->end, values, +1.);
411 // values is equal to integral of 1.
412 CPPUNIT_ASSERT_EQUAL( 1.+integral, grid->integral() );
413}
414
415/** UnitTest for operator+=()
416 */
417void SamplingGridTest::operatorPlusEqual_Test()
418{
419 // create other grid
420 const double begin[NDIM] = { 0., 0., 0. };
421 const double end[NDIM] = { 1., 1., 1. };
422 SamplingGrid::sampledvalues_t othervalues;
423 const double othergrid_value = 1.5;
424 for (size_t i=0; i< NUMBEROFSAMPLES(2); ++i)
425 othervalues += othergrid_value;
426 SamplingGrid othergrid(begin, end, 2, othervalues);
427 CPPUNIT_ASSERT_EQUAL( othergrid_value, *(othergrid.sampled_grid.begin()) );
428
429 // perform operation
430 CPPUNIT_ASSERT_NO_THROW( *grid += othergrid );
431
432 // check the contents of the grid
433 const double sum = grid_value+othergrid_value;
434 for (SamplingGrid::sampledvalues_t::const_iterator iter = grid->sampled_grid.begin();
435 iter != grid->sampled_grid.end(); ++iter)
436 CPPUNIT_ASSERT_EQUAL( sum, *iter );
437}
438
439/** UnitTest for operator-=()
440 */
441void SamplingGridTest::operatorMinusEqual_Test()
442{
443 // create other grid
444 const double begin[NDIM] = { 0., 0., 0. };
445 const double end[NDIM] = { 1., 1., 1. };
446 SamplingGrid::sampledvalues_t othervalues;
447 const double othergrid_value = 1.5;
448 for (size_t i=0; i< NUMBEROFSAMPLES(2); ++i)
449 othervalues += othergrid_value;
450 SamplingGrid othergrid(begin, end, 2, othervalues);
451 CPPUNIT_ASSERT_EQUAL( othergrid_value, *(othergrid.sampled_grid.begin()) );
452
453 // perform operation
454 CPPUNIT_ASSERT_NO_THROW( *grid -= othergrid );
455
456 // check the contents of the grid
457 const double difference = grid_value-othergrid_value;
458 for (SamplingGrid::sampledvalues_t::const_iterator iter = grid->sampled_grid.begin();
459 iter != grid->sampled_grid.end(); ++iter)
460 CPPUNIT_ASSERT_EQUAL( difference, *iter );
461}
462
463
464/** UnitTest for operator==()
465 */
466void SamplingGridTest::equality_Test()
467{
468 const double begin[NDIM] = { 0., 0., 0. };
469 const double otherbegin[NDIM] = { .5, 0.1, -0.5 };
470 const double end[NDIM] = { 1., 1., 1. };
471 const double otherend[NDIM] = { 2., 2., 2. };
472 const double begin_window[NDIM] = { 0., 0., 0. };
473 const double otherbegin_window[NDIM] = { .75, 0.1, 0. };
474 const double end_window[NDIM] = { 1., 1., 1. };
475 const double otherend_window[NDIM] = { .9, .9, .9 };
476
477 // create other grid
478 SamplingGrid samegrid(begin, end, 2, values);
479 SamplingGrid differentbegin(otherbegin, end, 2, values);
480 SamplingGrid differentend(begin, otherend, 2, values);
481 SamplingGrid::sampledvalues_t morevalues;
482 {
483 const double othergrid_value = 1.5;
484 for (size_t i=0; i< NUMBEROFSAMPLES(4); ++i)
485 morevalues += othergrid_value;
486 }
487 SamplingGrid differentlevel(begin, end, 4, morevalues);
488 SamplingGrid::sampledvalues_t othervalues;
489 {
490 const double othergrid_value = 1.5;
491 for (size_t i=0; i< NUMBEROFSAMPLES(2); ++i)
492 othervalues += othergrid_value;
493 }
494 SamplingGrid differentvalues(begin, end, 2, othervalues);
495
496 // check for same level, begin, and end
497 CPPUNIT_ASSERT( *grid == *grid );
498 CPPUNIT_ASSERT( *grid == samegrid );
499 CPPUNIT_ASSERT( samegrid == *grid);
500 CPPUNIT_ASSERT( *grid != differentbegin);
501 CPPUNIT_ASSERT( differentbegin != *grid);
502 CPPUNIT_ASSERT( *grid != differentend );
503 CPPUNIT_ASSERT( differentend != *grid );
504 CPPUNIT_ASSERT( *grid != differentlevel );
505 CPPUNIT_ASSERT( differentlevel != *grid );
506
507 // check for all but differing values
508 CPPUNIT_ASSERT( *grid != differentvalues );
509 CPPUNIT_ASSERT( differentvalues != *grid );
510
511 // check for different windows
512 SamplingGrid differentwindowbegin(begin, end, 2);
513 differentwindowbegin.setWindow(otherbegin_window, end_window);
514 SamplingGrid differentwindowend(begin, end, 2);
515 differentwindowend.setWindow(begin_window, otherend_window);
516 CPPUNIT_ASSERT( *grid != differentwindowbegin );
517 CPPUNIT_ASSERT( differentwindowbegin != *grid );
518 CPPUNIT_ASSERT( *grid != differentwindowend );
519 CPPUNIT_ASSERT( differentwindowend != *grid );
520
521 // check against ZeroInstance
522 CPPUNIT_ASSERT( *grid != ZeroInstance<SamplingGrid>() );
523 CPPUNIT_ASSERT( samegrid != ZeroInstance<SamplingGrid>() );
524 CPPUNIT_ASSERT( differentbegin != ZeroInstance<SamplingGrid>() );
525 CPPUNIT_ASSERT( differentend != ZeroInstance<SamplingGrid>() );
526 CPPUNIT_ASSERT( differentlevel != ZeroInstance<SamplingGrid>() );
527 CPPUNIT_ASSERT( differentvalues != ZeroInstance<SamplingGrid>() );
528 CPPUNIT_ASSERT( differentwindowbegin != ZeroInstance<SamplingGrid>() );
529 CPPUNIT_ASSERT( differentwindowend != ZeroInstance<SamplingGrid>() );
530}
531
532/** UnitTest for serialization
533 */
534void SamplingGridTest::serializeTest()
535{
536 // serialize
537 std::stringstream outputstream;
538 boost::archive::text_oarchive oa(outputstream);
539 oa << grid;
540
541 // deserialize
542 SamplingGrid *samegrid = NULL;
543 std::stringstream returnstream(outputstream.str());
544 boost::archive::text_iarchive ia(returnstream);
545 ia >> samegrid;
546
547 CPPUNIT_ASSERT( samegrid != NULL );
548 CPPUNIT_ASSERT( *grid == *samegrid );
549
550 delete samegrid;
551}
552
553#ifdef HAVE_INLINE
554inline
555#endif
556static int calculateIndex(const int N[NDIM], const int &_length)
557{
558 return N[2] + N[1]*_length + N[0]*_length*_length;
559}
560
561#ifdef HAVE_INLINE
562inline
563#endif
564static double calculateDistanceSquared(const int N[NDIM], const int &_length)
565{
566 return
567 ::pow(N[0]/(double)_length-.5,2)
568 + ::pow(N[1]/(double)_length-.5,2)
569 + ::pow(N[2]/(double)_length-.5,2);
570}
571
572#ifdef HAVE_INLINE
573inline
574#endif
575static double getBoundaryCaseFactor(const int N[NDIM], const int &_length)
576{
577 static double third_two=::pow(4., 1./3.);
578 double returnthreshold = 1.;
579 for (size_t i=0;i<NDIM;++i)
580 if ((N[i] == 0) || (N[i] == _length-1))
581 returnthreshold *= third_two;
582 return returnthreshold;
583}
584
585/** UnitTest for downsample()
586 */
587void SamplingGridTest::downsample_gridTest()
588{
589 const double begin[NDIM] = { 0., 0., 0. };
590 const double end[NDIM] = { 1., 1., 1. };
591
592 // simple test, one level difference, same value everywhere
593 {
594 SamplingGrid::sampledvalues_t checkvalues;
595 SamplingGrid::sampledvalues_t othervalues;
596 const double othergrid_value = 1.5;
597 for (size_t i=0; i< NUMBEROFSAMPLES(2); ++i)
598 checkvalues += othergrid_value;
599 for (size_t i=0; i< NUMBEROFSAMPLES(3); ++i)
600 othervalues += othergrid_value;
601
602 SamplingGrid largegrid(begin, end, 3, othervalues);
603// std::cout << " largegrid value " << largegrid.sampled_grid << std::endl;
604 SamplingGrid smallgrid(begin, end, 2);
605 SamplingGrid::downsample(smallgrid, largegrid, 2);
606 SamplingGrid checkgrid(begin, end, 2, checkvalues);
607// std::cout << " smallgrid value " << smallgrid.sampled_grid << std::endl;
608// std::cout << " checkgrid value " << checkgrid.sampled_grid << std::endl;
609 CPPUNIT_ASSERT_EQUAL( smallgrid, checkgrid );
610 }
611
612 // simple test, two level difference, same value everywhere
613 {
614 SamplingGrid::sampledvalues_t checkvalues;
615 SamplingGrid::sampledvalues_t othervalues;
616 const double othergrid_value = 1.5;
617 for (size_t i=0; i< NUMBEROFSAMPLES(2); ++i)
618 checkvalues += othergrid_value;
619 for (size_t i=0; i< NUMBEROFSAMPLES(4); ++i)
620 othervalues += othergrid_value;
621
622 SamplingGrid largegrid(begin, end, 4, othervalues);
623// std::cout << " largegrid value " << largegrid.sampled_grid << std::endl;
624 SamplingGrid smallgrid(begin, end, 2);
625 SamplingGrid::downsample(smallgrid, largegrid, 2);
626 SamplingGrid checkgrid(begin, end, 2, checkvalues);
627// std::cout << " smallgrid value " << smallgrid.sampled_grid << std::endl;
628// std::cout << " checkgrid value " << checkgrid.sampled_grid << std::endl;
629 CPPUNIT_ASSERT_EQUAL( smallgrid, checkgrid );
630 }
631
632 // same grid, window equals grids, ever larger largegrids
633 const int base_level = 2;
634 for (int grid_difference = 1; grid_difference <= 3; ++grid_difference) {
635// LOG(2, "Checking with difference " << grid_difference);
636 const int length_c = ::pow(2, base_level);
637 const int length_f = ::pow(2, base_level+grid_difference);
638 SamplingGrid::sampledvalues_t checkvalues((int)::pow(length_c, (int)NDIM), 0.);
639 SamplingGrid::sampledvalues_t othervalues((int)::pow(length_f, (int)NDIM), 0.);
640 int N[NDIM];
641 for (N[0]=0; N[0]< length_f; ++N[0]) {
642 for (N[1]=0; N[1]< length_f; ++N[1]) {
643 for (N[2]=0; N[2]< length_f; ++N[2]) {
644 const int index = calculateIndex(N, length_f);
645 const double dist = calculateDistanceSquared(N, length_f);
646 othervalues[index] = cos(M_PI*dist/1.5);
647 }
648 }
649 }
650 for (N[0]=0; N[0]< length_c; ++N[0]) {
651 for (N[1]=0; N[1]< length_c; ++N[1]) {
652 for (N[2]=0; N[2]< length_c; ++N[2]) {
653 const int index = calculateIndex(N, length_c);
654 const double dist = calculateDistanceSquared(N, length_c);
655 checkvalues[index] = cos(M_PI*dist/1.5);
656 }
657 }
658 }
659
660 SamplingGrid largegrid(begin, end, base_level+grid_difference, othervalues);
661// std::cout << " largegrid value " << largegrid.sampled_grid << std::endl;
662 SamplingGrid smallgrid(begin, end, base_level);
663 SamplingGrid::downsample(smallgrid, largegrid, base_level);
664 SamplingGrid checkgrid(begin, end, base_level, checkvalues);
665// std::cout << " smallgrid value " << smallgrid.sampled_grid << std::endl;
666// std::cout << " checkgrid value " << checkgrid.sampled_grid << std::endl;
667 const double threshold = 3.2e-2;
668 // we skip the first value as checkvalues[0] is always zero, hard to get from downsampling
669 for (N[0]=1; N[0]< length_c; ++N[0])
670 for (N[1]=0; N[1]< length_c; ++N[1])
671 for (N[2]=0; N[2]< length_c; ++N[2]) {
672 const double check_threshold =
673 threshold*(1.+grid_difference/4.)*getBoundaryCaseFactor(N, length_c);
674 const int index = calculateIndex(N, length_c);
675// std::cout << "Comparing "
676// << fabs((smallgrid.sampled_grid[index] - checkgrid.sampled_grid[index]))
677// << " < " << check_threshold << std::endl;
678 CPPUNIT_ASSERT(
679 fabs((smallgrid.sampled_grid[index] - checkgrid.sampled_grid[index])) < check_threshold);
680// if (fabs(checkgrid.sampled_grid[index]) > 1e-10) {
681// std::cout << "Comparing "
682// << fabs((smallgrid.sampled_grid[index] - checkgrid.sampled_grid[index])/checkgrid.sampled_grid[index])
683// << " < " << check_threshold << std::endl;
684// CPPUNIT_ASSERT(
685// fabs((smallgrid.sampled_grid[index] - checkgrid.sampled_grid[index])/checkgrid.sampled_grid[index]) < check_threshold);
686// }
687 }
688 }
689}
690
691/** UnitTest for downsample()
692 */
693void SamplingGridTest::downsample_smallerwindowTest()
694{
695 const double begin[NDIM] = { 0., 0., 0. };
696 const double end[NDIM] = { 2., 2., 2. };
697
698 // same grid, window is half of grid, different level by one
699 const int base_level = 3;
700 for (int grid_difference = 1; grid_difference <= 3; ++grid_difference) {
701// LOG(2, "Checking with difference " << grid_difference);
702 const int window_length_c = ::pow(2, base_level-1);
703 const int window_length_f = ::pow(2, base_level+grid_difference-1);
704 SamplingGrid::sampledvalues_t checkvalues((int)::pow(window_length_c, (int)NDIM), 0.);
705 SamplingGrid::sampledvalues_t othervalues((int)::pow(window_length_f, (int)NDIM), 0.);
706 int N[NDIM];
707 for (N[0]=0; N[0]< window_length_f; ++N[0]) {
708 for (N[1]=0; N[1]< window_length_f; ++N[1]) {
709 for (N[2]=0; N[2]< window_length_f; ++N[2]) {
710 const int index = calculateIndex(N, window_length_f);
711 const double dist = calculateDistanceSquared(N, window_length_f);
712 othervalues[index] = cos(M_PI*dist/1.5);
713 }
714 }
715 }
716 for (N[0]=0; N[0]< window_length_c; ++N[0]) {
717 for (N[1]=0; N[1]< window_length_c; ++N[1]) {
718 for (N[2]=0; N[2]< window_length_c; ++N[2]) {
719 const int index = calculateIndex(N, window_length_c);
720 const double dist = calculateDistanceSquared(N, window_length_c);
721 checkvalues[index] = cos(M_PI*dist/1.5);
722 }
723 }
724 }
725
726 /** Here, we must initialize the larger grid with zero window first and
727 * then add the values into the smaller window.
728 */
729 SamplingGrid largegrid(begin, end, base_level+grid_difference);
730 const double window_begin[NDIM] = {
731 largegrid.getNearestHigherGridPoint(0.5, 0),
732 largegrid.getNearestHigherGridPoint(0.5, 1),
733 largegrid.getNearestHigherGridPoint(0.5, 2) };
734 const double window_end[NDIM] = {
735 largegrid.getNearestLowerGridPoint(1.5, 0),
736 largegrid.getNearestLowerGridPoint(1.5, 1),
737 largegrid.getNearestLowerGridPoint(1.5, 2) };
738 largegrid.setWindow(window_begin, window_end);
739 largegrid.addOntoWindow(window_begin, window_end, othervalues, +1.);
740// std::cout << " largegrid value " << largegrid.sampled_grid << std::endl;
741
742 // smallgrid is downsample from full large grid
743 SamplingGrid smallgrid(begin, end, base_level);
744 SamplingGrid::downsample(smallgrid, largegrid, base_level);
745// std::cout << " smallgrid value " << smallgrid.sampled_grid << std::endl;
746
747 // checkgrid is created in the same way as the large grid (only with smaller level)
748 SamplingGrid checkgrid(begin, end, base_level);
749 checkgrid.setWindow(window_begin, window_end);
750 checkgrid.addOntoWindow(window_begin, window_end, checkvalues, +1.);
751// std::cout << " checkgrid value " << checkgrid.sampled_grid << std::endl;
752
753 // then we compare over the full length
754 /** Note that the threshold does not get better with increasing grid_difference,
755 * on the contrary! For a grid_difference of 1, the finer grid is exact as it
756 * directly sampled from the function. For a larger grid_difference, the finer
757 * grid (being one level away from the desired coarse grid) is just an
758 * approximation although obtained from a finer sampling. Hence, the larger the
759 * grid_difference, the worse is the smallgrid with respect to checkgrid.
760 */
761 const double threshold = 3.2e-2;
762 // we skip the first value as checkvalues[0] is always zero, hard to get from downsampling
763 for (N[0]=1; N[0]< window_length_c; ++N[0])
764 for (N[1]=0; N[1]< window_length_c; ++N[1])
765 for (N[2]=0; N[2]< window_length_c; ++N[2]) {
766 const double check_threshold =
767 threshold*(1.+grid_difference/4.)*getBoundaryCaseFactor(N, window_length_c);
768 const int index = calculateIndex(N, window_length_c);
769 const double difference = fabs((smallgrid.sampled_grid[index] - checkgrid.sampled_grid[index]));
770// std::cout << "Comparing |"
771// << scientific
772// << smallgrid.sampled_grid[index] << " - "
773// << checkgrid.sampled_grid[index] << "| = "
774// << fabs((smallgrid.sampled_grid[index] - checkgrid.sampled_grid[index]))
775// << " < " << check_threshold << " => "
776// << fixed << setprecision(2)
777// << 100*difference/threshold
778// << " %, compare to " << 100*(1.+grid_difference/4.)*getBoundaryCaseFactor(N, window_length_c)
779// << " %" << std::endl;
780 CPPUNIT_ASSERT( difference < check_threshold );
781 }
782 }
783}
Note: See TracBrowser for help on using the repository browser.