8 #ifndef TEST_DISTRIBUTION_DISTRIBUTIONMETHODS_H_
9 #define TEST_DISTRIBUTION_DISTRIBUTIONMETHODS_H_
17 #define ECKIT_TESTING_SELF_REGISTER_CASES 0
19 #include "eckit/config/LocalConfiguration.h"
20 #include "eckit/mpi/Comm.h"
21 #include "eckit/testing/Test.h"
23 #include "oops/mpi/mpi.h"
24 #include "oops/runs/Test.h"
25 #include "oops/test/TestEnvironment.h"
26 #include "oops/util/Logger.h"
28 #include "ioda/distribution/Accumulator.h"
29 #include "ioda/distribution/Distribution.h"
30 #include "ioda/distribution/DistributionFactory.h"
40 auto accumulator = TestDist.createAccumulator<T>();
41 for (
size_t loc = 0; loc < myRecords.size(); ++loc)
42 accumulator->addTerm(loc, myRecords[loc]);
43 const T sum = accumulator->computeResult();
44 EXPECT_EQUAL(sum,
static_cast<T
>(expectedSum));
50 const size_t numSums = 3;
51 std::vector<T> expectedSums(numSums);
52 for (
size_t i = 0; i < numSums; ++i)
53 expectedSums[i] = (i + 1) * expectedSum;
57 auto accumulator = TestDist.createAccumulator<T>(numSums);
58 std::vector<T> terms(numSums);
59 for (
size_t loc = 0; loc < myRecords.size(); ++loc) {
60 for (
size_t i = 0; i < numSums; ++i)
61 terms[i] = (i + 1) * myRecords[loc];
62 accumulator->addTerm(loc, terms);
64 std::vector<T> sums = accumulator->computeResult();
66 EXPECT_EQUAL(sums, expectedSums);
71 auto accumulator = TestDist.createAccumulator<T>(numSums);
72 std::vector<T> terms(numSums);
73 for (
size_t loc = 0; loc < myRecords.size(); ++loc)
74 for (
size_t i = 0; i < numSums; ++i)
75 accumulator->addTerm(loc, i, (i + 1) * myRecords[loc]);
76 std::vector<T> sums = accumulator->computeResult();
78 EXPECT_EQUAL(sums, expectedSums);
86 T max = std::numeric_limits<T>::lowest();
87 for (
size_t loc = 0; loc < myRecords.size(); ++loc)
88 max = std::max<T>(max, myRecords[loc]);
93 EXPECT_EQUAL(max, expectedMax);
102 std::vector<T> maxes(2, std::numeric_limits<T>::lowest());
103 for (
size_t loc = 0; loc < myRecords.size(); ++loc) {
104 maxes[0] = std::max<T>(maxes[0], myRecords[loc]);
105 maxes[1] = std::max<T>(maxes[1], myRecords[loc] + shift);
110 const std::vector<T> expectedMaxes{
static_cast<T
>(expectedMax),
111 static_cast<T
>(expectedMax + shift)};
113 EXPECT_EQUAL(maxes, expectedMaxes);
116 template <
typename T>
118 size_t expectedMin) {
120 T min = std::numeric_limits<T>::max();
121 for (
size_t loc = 0; loc < myRecords.size(); ++loc)
122 min = std::min<T>(min, myRecords[loc]);
127 EXPECT_EQUAL(min, expectedMin);
130 template <
typename T>
132 size_t expectedMin) {
136 std::vector<T> mins(2, std::numeric_limits<T>::max());
137 for (
size_t loc = 0; loc < myRecords.size(); ++loc) {
138 mins[0] = std::min<T>(mins[0], myRecords[loc]);
139 mins[1] = std::min<T>(mins[1], myRecords[loc] + shift);
144 const std::vector<T> expectedMins{
static_cast<T
>(expectedMin),
145 static_cast<T
>(expectedMin + shift)};
147 EXPECT_EQUAL(mins, expectedMins);
151 eckit::LocalConfiguration conf(::test::TestEnvironment::config());
153 const eckit::mpi::Comm & MpiComm = oops::mpi::world();
154 const std::size_t MyRank = MpiComm.rank();
155 const std::size_t nprocs = MpiComm.size();
157 std::vector<eckit::LocalConfiguration> dist_types;
158 conf.get(
"distribution types", dist_types);
159 for (std::size_t i = 0; i < dist_types.size(); ++i) {
160 eckit::LocalConfiguration DistConfig = dist_types[i];
161 oops::Log::debug() <<
"Distribution::DistributionTypes: conf: "
162 << DistConfig << std::endl;
165 const std::string DistName = TestDist->name();
168 size_t Gnlocs = nprocs;
169 std::vector<double> glats(Gnlocs, 0.0);
170 std::vector<double> glons(Gnlocs, 0.0);
171 std::vector<size_t> myRecords;
172 for (std::size_t j = 0; j < Gnlocs; ++j) {
173 glons[j] = j*360.0/Gnlocs;
174 eckit::geometry::Point2 point(glons[j], glats[j]);
175 TestDist->assignRecord(j, j, point);
176 if (TestDist->isMyRecord(j))
177 myRecords.push_back(j);
179 TestDist->computePatchLocs();
183 size_t expectedSum = 0;
184 for (std::size_t i = 0; i < nprocs; i++) {
188 const size_t expectedMax = nprocs - 1;
190 const size_t expectedMin = 0;
192 testAccumulateScalar<double>(*TestDist, myRecords, expectedSum);
193 testAccumulateScalar<float>(*TestDist, myRecords, expectedSum);
194 testAccumulateScalar<int>(*TestDist, myRecords, expectedSum);
195 testAccumulateScalar<size_t>(*TestDist, myRecords, expectedSum);
196 testAccumulateVector<double>(*TestDist, myRecords, expectedSum);
197 testAccumulateVector<float>(*TestDist, myRecords, expectedSum);
198 testAccumulateVector<int>(*TestDist, myRecords, expectedSum);
199 testAccumulateVector<size_t>(*TestDist, myRecords, expectedSum);
201 testMaxScalar<double>(*TestDist, myRecords, expectedMax);
202 testMaxScalar<float>(*TestDist, myRecords, expectedMax);
203 testMaxScalar<int>(*TestDist, myRecords, expectedMax);
204 testMaxScalar<size_t>(*TestDist, myRecords, expectedMax);
205 testMaxVector<double>(*TestDist, myRecords, expectedMax);
206 testMaxVector<float>(*TestDist, myRecords, expectedMax);
207 testMaxVector<int>(*TestDist, myRecords, expectedMax);
208 testMaxVector<size_t>(*TestDist, myRecords, expectedMax);
210 testMinScalar<double>(*TestDist, myRecords, expectedMin);
211 testMinScalar<float>(*TestDist, myRecords, expectedMin);
212 testMinScalar<int>(*TestDist, myRecords, expectedMin);
213 testMinScalar<size_t>(*TestDist, myRecords, expectedMin);
214 testMinVector<double>(*TestDist, myRecords, expectedMin);
215 testMinVector<float>(*TestDist, myRecords, expectedMin);
216 testMinVector<int>(*TestDist, myRecords, expectedMin);
217 testMinVector<size_t>(*TestDist, myRecords, expectedMin);
229 std::string
testid()
const override {
return "test::DistributionMethods";}
232 std::vector<eckit::testing::Test>& ts = eckit::testing::specification();
234 ts.emplace_back(
CASE(
"distribution/Distribution/testDistributionMethods")
static std::unique_ptr< Distribution > create(const eckit::mpi::Comm &comm, const eckit::Configuration &config)
Create a Distribution object implementing a particular method of distributing observations across mul...
void register_tests() const override
virtual ~DistributionMethods()
std::string testid() const override
void clear() const override
void testAccumulateScalar(const Distribution &TestDist, const std::vector< size_t > &myRecords, size_t expectedSum)
void testMinVector(const Distribution &TestDist, const std::vector< size_t > &myRecords, size_t expectedMin)
CASE("Derived variable, unit conversion, and exception checking methods")
void testMinScalar(const Distribution &TestDist, const std::vector< size_t > &myRecords, size_t expectedMin)
void testMaxVector(const Distribution &TestDist, const std::vector< size_t > &myRecords, size_t expectedMax)
void testDistributionMethods()
void testMaxScalar(const Distribution &TestDist, const std::vector< size_t > &myRecords, size_t expectedMax)
void testAccumulateVector(const Distribution &TestDist, const std::vector< size_t > &myRecords, size_t expectedSum)