AzimuthalIntegrationProfile: Add standard deviation + save pixel count + improve handling of special cases (missing image)

This commit is contained in:
2026-06-02 15:50:11 +02:00
parent 75de40f52b
commit 953089009f
13 changed files with 175 additions and 16 deletions
+70 -8
View File
@@ -171,18 +171,19 @@ TEST_CASE("AzimuthalIntegrationProfile","[AzimuthalIntegration]") {
AzimuthalIntegrationProfile profile(mapping);
std::vector<float> sum(mapping.GetBinNumber());
std::vector<float> sum(mapping.GetBinNumber()), sum2(mapping.GetBinNumber());
std::vector<uint32_t> count(mapping.GetBinNumber());
for (int i = 0; i < mapping.GetBinNumber(); i++) {
sum[i] = i * i * 4;
sum2[i] = i * i * i * i * 4;
count[i] = i;
}
REQUIRE_NOTHROW(profile.Add(sum, count));
REQUIRE_NOTHROW(profile.Add(sum, count));
REQUIRE_NOTHROW(profile.Add(sum, sum2, count));
REQUIRE_NOTHROW(profile.Add(sum, sum2, count));
std::vector<float> sum_wr(mapping.GetBinNumber() - 1);
REQUIRE_THROWS(profile.Add(sum_wr, count));
REQUIRE_THROWS(profile.Add(sum_wr, sum2, count));
auto plot = profile.GetPlot();
REQUIRE(plot.GetPlots().size() == 1);
@@ -198,6 +199,63 @@ TEST_CASE("AzimuthalIntegrationProfile","[AzimuthalIntegration]") {
}
}
TEST_CASE("AzimuthalIntegrationProfile_GetStd","[AzimuthalIntegration]") {
DiffractionExperiment x(DetJF4M());
x.DetectorDistance_mm(50).BeamX_pxl(1000).BeamY_pxl(1000);
x.QSpacingForAzimInt_recipA(0.1).QRangeForAzimInt_recipA(0.1, 4);
PixelMask pixel_mask(x);
AzimuthalIntegrationMapping mapping(x, pixel_mask);
AzimuthalIntegrationProfile profile(mapping);
REQUIRE(mapping.GetBinNumber() >= 4);
std::vector<float> sum(mapping.GetBinNumber()), sum2(mapping.GetBinNumber());
std::vector<uint32_t> count(mapping.GetBinNumber());
sum[0] = 2 + 3 + 4 + 5;
sum2[0] = 4 + 9 + 16 + 25;
count[0] = 4;
sum[1] = 1 + 1;
sum2[1] = 1 + 1;
count[1] = 2;
sum[2] = 1;
sum2[2] = 1;
count[2] = 1;
sum[3] = 0;
sum2[3] = 0;
count[3] = 0;
REQUIRE_NOTHROW(profile.Add(sum, sum2, count));
auto ret_mean = profile.GetResult();
auto ret_stddev = profile.GetStd();
auto ret_count = profile.GetPixelCount();
REQUIRE(ret_mean.size() == mapping.GetBinNumber());
REQUIRE(ret_stddev.size() == mapping.GetBinNumber());
REQUIRE(ret_count.size() == mapping.GetBinNumber());
CHECK(ret_mean[0] == Catch::Approx(3.5));
CHECK(ret_stddev[0] == Catch::Approx(std::sqrt(5.0/ 3.0)));
CHECK(ret_count[0] == 4);
CHECK(ret_mean[1] == Catch::Approx(1.0));
CHECK(ret_stddev[1] == 0.0f);
CHECK(ret_count[1] == 2);
CHECK(ret_mean[2] == Catch::Approx(1.0));
CHECK(std::isnan(ret_stddev[2]));
CHECK(ret_count[2] == 1);
CHECK(std::isnan(ret_mean[3]));
CHECK(std::isnan(ret_stddev[3]));
CHECK(ret_count[3] == 0);
}
TEST_CASE("AzimuthalIntegrationProfile_operatorAdd","[AzimuthalIntegration]") {
DiffractionExperiment x(DetJF4M());
x.DetectorDistance_mm(50).BeamX_pxl(1000).BeamY_pxl(1000);
@@ -208,14 +266,15 @@ TEST_CASE("AzimuthalIntegrationProfile_operatorAdd","[AzimuthalIntegration]") {
AzimuthalIntegrationProfile profile0(mapping), profile1(mapping);
std::vector<float> sum(mapping.GetBinNumber());
std::vector<float> sum(mapping.GetBinNumber()), sum2(mapping.GetBinNumber());
std::vector<uint32_t> count(mapping.GetBinNumber());
for (int i = 0; i < mapping.GetBinNumber(); i++) {
sum[i] = (i + 1) * i * 4;
sum2[i] = (i+ 1) * i * 5;
count[i] = i + 1;
}
REQUIRE_NOTHROW(profile0.Add(sum, count));
REQUIRE_NOTHROW(profile0.Add(sum, sum2, count));
REQUIRE_NOTHROW(profile1 += profile0);
auto plot = profile1.GetPlot();
@@ -240,13 +299,15 @@ TEST_CASE("AzimuthalIntegrationProfile_GetMeanValueOfBins","[AzimuthalIntegratio
AzimuthalIntegrationProfile profile(mapping);
std::vector<float> sum(mapping.GetBinNumber());
std::vector<float> sum2(mapping.GetBinNumber());
std::vector<uint32_t> count(mapping.GetBinNumber());
for (int i = 0; i < mapping.GetBinNumber(); i++) {
sum[i] = i * i * 4;
sum2[i] = i * i * i * i * 4;
count[i] = i;
}
REQUIRE_NOTHROW(profile.Add(sum, count));
REQUIRE_NOTHROW(profile.Add(sum, sum2, count));
REQUIRE(profile.GetMeanValueOfBins(0,2) == Catch::Approx((sum[0] + sum[1] + sum[2]) / double(count[0] + count[1] + count[2])));
REQUIRE(profile.GetMeanValueOfBins(5,7) == Catch::Approx((sum[5] + sum[6] + sum[7]) / double (count[5] + count[6] + count[7])));
@@ -276,6 +337,7 @@ TEST_CASE("AzimuthalIntegrationProfile_GetResult1D","[AzimuthalIntegration]") {
REQUIRE(mapping.GetBinNumber() == 9);
std::vector<float> sum(mapping.GetBinNumber(), 0.0f);
std::vector<float> sum2(mapping.GetBinNumber(), 20.0f);
std::vector<uint32_t> count(mapping.GetBinNumber(), 0);
// Layout is [azimuth][q], flattened:
@@ -299,7 +361,7 @@ TEST_CASE("AzimuthalIntegrationProfile_GetResult1D","[AzimuthalIntegration]") {
sum[7] = 31; count[7] = 1; // az2 q1
sum[8] = 32; count[8] = 1; // az2 q2
REQUIRE_NOTHROW(profile.Add(sum, count));
REQUIRE_NOTHROW(profile.Add(sum, sum2, count));
auto result_1d = profile.GetResult1D();