Revert "integration: the background is fitted over the ring that survives, not averaged over it"
Build Packages / build:windows:nocuda (push) Successful in 17m27s
Build Packages / build:windows:cuda (push) Successful in 19m59s
Build Packages / build:rugnux:aarch64 (cross) (push) Successful in 9m47s
Build Packages / build:rugnux-tgz (x86_64) (push) Successful in 14m51s
Build Packages / build:viewer-tgz:cpu (push) Successful in 18m35s
Build Packages / build:rugnux:windows (push) Successful in 11m12s
Build Packages / build:viewer-tgz:cuda (push) Successful in 19m19s
Build Packages / build:rpm (rocky9_nocuda) (push) Successful in 20m1s
Build Packages / build:rpm (rocky8_nocuda) (push) Successful in 22m38s
Build Packages / build:rpm (ubuntu2204_nocuda) (push) Successful in 19m53s
Build Packages / build:rpm (ubuntu2404_nocuda) (push) Successful in 20m23s
Build Packages / build:rpm (rocky9_sls9) (push) Successful in 21m56s
Build Packages / build:rpm (rocky8_sls9) (push) Successful in 27m1s
Build Packages / build:rpm (rocky9) (push) Successful in 21m37s
Build Packages / build:rpm (rocky8) (push) Successful in 24m50s
Build Packages / XDS test (durin plugin) (push) Successful in 10m42s
Build Packages / Generate python client (push) Successful in 17s
Build Packages / build:rpm (ubuntu2404) (push) Successful in 20m18s
Build Packages / Create release (push) Skipped
Build Packages / build:rpm (ubuntu2204) (push) Successful in 24m50s
Build Packages / Build documentation (push) Successful in 43s
Build Packages / XDS test (neggia plugin) (push) Successful in 10m9s
Build Packages / XDS test (JFJoch plugin) (push) Successful in 11m5s
Build Packages / DIALS test (push) Successful in 18m12s
Build Packages / Unit tests (push) Successful in 1h27m12s
Build Packages / build:windows:nocuda (push) Successful in 17m27s
Build Packages / build:windows:cuda (push) Successful in 19m59s
Build Packages / build:rugnux:aarch64 (cross) (push) Successful in 9m47s
Build Packages / build:rugnux-tgz (x86_64) (push) Successful in 14m51s
Build Packages / build:viewer-tgz:cpu (push) Successful in 18m35s
Build Packages / build:rugnux:windows (push) Successful in 11m12s
Build Packages / build:viewer-tgz:cuda (push) Successful in 19m19s
Build Packages / build:rpm (rocky9_nocuda) (push) Successful in 20m1s
Build Packages / build:rpm (rocky8_nocuda) (push) Successful in 22m38s
Build Packages / build:rpm (ubuntu2204_nocuda) (push) Successful in 19m53s
Build Packages / build:rpm (ubuntu2404_nocuda) (push) Successful in 20m23s
Build Packages / build:rpm (rocky9_sls9) (push) Successful in 21m56s
Build Packages / build:rpm (rocky8_sls9) (push) Successful in 27m1s
Build Packages / build:rpm (rocky9) (push) Successful in 21m37s
Build Packages / build:rpm (rocky8) (push) Successful in 24m50s
Build Packages / XDS test (durin plugin) (push) Successful in 10m42s
Build Packages / Generate python client (push) Successful in 17s
Build Packages / build:rpm (ubuntu2404) (push) Successful in 20m18s
Build Packages / Create release (push) Skipped
Build Packages / build:rpm (ubuntu2204) (push) Successful in 24m50s
Build Packages / Build documentation (push) Successful in 43s
Build Packages / XDS test (neggia plugin) (push) Successful in 10m9s
Build Packages / XDS test (JFJoch plugin) (push) Successful in 11m5s
Build Packages / DIALS test (push) Successful in 18m12s
Build Packages / Unit tests (push) Successful in 1h27m12s
This reverts commit 6a3ae9c65.
The rotation battery refuses it. The median is clean - zero movement in R_meas and CC1/2, most
crystals untouched or moving in the third decimal, which is what was predicted - but the tail is
not a cost, it is a failure: one crystal's CC1/2 falls from 91.3% to 6.8% with its reflection and
observation counts essentially unchanged, so the intensities are being corrupted rather than the
weak ones discarded. Another loses seven points of R_meas and half its ISa; a third has its
high-shell CC1/2 go negative; a fourth's ISa doubles, which is an error model measuring something
different rather than measuring better.
The change was predicted to cost one to two points of high-shell CC1/2 on crowded patterns, and
that prediction was made on six geometries. Fifty-one say otherwise.
The defect it fixes is real and stays on the record: within the outer background radius of the
array edge the ring is truncated inward while the disk is not, so the surviving ring sits where
the radial background is higher and the reflection reads low - measured at 1.79 counts per pixel
four pixels from a border, and confirmed by a masked gap producing the same bias signed by the
direction of its displacement. Fitting the background over the surviving ring is the right shape
of answer. Doing it per reflection, from a ring that a neighbour mask has often already truncated,
is evidently not.
Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01EFEJG6WBQv8th4UJFNe53N
This commit is contained in:
1 parent
6a3ae9c658
commit
b650cda037
9 files changed
+20
-313
No files matched your search
@@ -45,26 +45,17 @@ Reflection MakeReflection(float x, float y, float d, int hkl) {
|
||||
// centre of every 5th, a mid-profile pixel of every 7th and a disk-edge pixel of every 11th. That is
|
||||
// the MINPK rescue's own case - a reflection kept and fitted over the pixels it has - and with it the
|
||||
// peak-loss rule, which has to fire on the same reflections in both engines.
|
||||
// border > 0 puts a radial background ramp of that many counts per pixel of radius under the scene
|
||||
// and moves the spot grid onto the edges of the array, so the r2..r3 ring of the outermost spots is
|
||||
// truncated by the boundary. That is the case the radial-linear background fit exists for, and the
|
||||
// two engines have to fit the same line over the pixels each of them kept.
|
||||
Scene BuildScene(size_t width, size_t height, int spacing = 60, float companion_dx = 0.0f,
|
||||
bool clip_spots = false, float border = 0.0f) {
|
||||
bool clip_spots = false) {
|
||||
Scene s;
|
||||
s.width = width;
|
||||
s.height = height;
|
||||
s.image.assign(width * height, 12); // flat background
|
||||
if (border > 0.0f)
|
||||
for (size_t y = 0; y < height; ++y)
|
||||
for (size_t x = 0; x < width; ++x)
|
||||
s.image[y * width + x] = 200 + static_cast<int32_t>(std::lround(
|
||||
border * std::hypot(static_cast<double>(x) - 400.0, static_cast<double>(y) - 400.0)));
|
||||
|
||||
// A grid of spots, well separated so background rings do not overlap the neighbours' disks.
|
||||
// A spread of intensities (some weak, some very strong) and a spread of d (so several resolution
|
||||
// shells are populated) exercises the strong-spot selection, shell learning and the fit.
|
||||
const int margin = border > 0.0f ? 3 : 45;
|
||||
const int margin = 45;
|
||||
int hkl = 1;
|
||||
for (int gy = 0; margin + gy * spacing < static_cast<int>(height) - margin; ++gy) {
|
||||
for (int gx = 0; margin + gx * spacing < static_cast<int>(width) - margin; ++gx) {
|
||||
@@ -154,7 +145,7 @@ void CompareCpuVsGpu(IntegratorMode mode, std::optional<float> bandwidth_fwhm,
|
||||
float stencil_k = 0.0f,
|
||||
float r1 = 0.0f, float r2 = 0.0f, float r3 = 0.0f,
|
||||
OverlapMode overlap = OverlapMode::Off, float companion_dx = 0.0f,
|
||||
bool clip_spots = false, float border = 0.0f) {
|
||||
bool clip_spots = false) {
|
||||
const DiffractionExperiment experiment =
|
||||
MakeExperiment(mode, bandwidth_fwhm, clip_nsigma, radial, DetJF(2), stencil_k, r1, r2, r3,
|
||||
overlap);
|
||||
@@ -163,7 +154,7 @@ void CompareCpuVsGpu(IntegratorMode mode, std::optional<float> bandwidth_fwhm,
|
||||
const size_t npixel = experiment.GetPixelsNum();
|
||||
REQUIRE(npixel == width * height);
|
||||
|
||||
const Scene scene = BuildScene(width, height, spacing, companion_dx, clip_spots, border);
|
||||
const Scene scene = BuildScene(width, height, spacing, companion_dx, clip_spots);
|
||||
REQUIRE(scene.image.size() == npixel);
|
||||
REQUIRE(scene.predicted.size() > 60);
|
||||
|
||||
@@ -192,7 +183,7 @@ void CompareCpuVsGpu(IntegratorMode mode, std::optional<float> bandwidth_fwhm,
|
||||
if (clip_spots) {
|
||||
// Guard against the coverage going vacuous: the punched pixels have to actually cost some
|
||||
// reflections, or the two engines are being compared on a case neither of them meets.
|
||||
const Scene clean_scene = BuildScene(width, height, spacing, companion_dx, false, border);
|
||||
const Scene clean_scene = BuildScene(width, height, spacing, companion_dx, false);
|
||||
ImagePreprocessorBuffer clean_image(npixel);
|
||||
for (size_t i = 0; i < npixel; ++i)
|
||||
clean_image[i] = clean_scene.image[i];
|
||||
@@ -302,22 +293,6 @@ TEST_CASE("BraggIntegrationEngineGPU_MatchesCPU") {
|
||||
CompareCpuVsGpu(IntegratorMode::BoxSum, std::nullopt, 4.0f, false, 60, 0.0f,
|
||||
0.0f, 0.0f, 0.0f, OverlapMode::Off, 0.0f, true);
|
||||
}
|
||||
// Spots on the edges of the array under a radial background ramp: their background rings are
|
||||
// truncated by the boundary, so the radial-linear fit that replaces the ring mean has a different
|
||||
// pixel set - and a different line - for every one of them. The clip and the trim select that
|
||||
// pixel set differently in the two engines, so both estimators need the case.
|
||||
SECTION("ProfileGaussian border gradient") {
|
||||
CompareCpuVsGpu(IntegratorMode::ProfileGaussian, std::nullopt, 4.0f, false, 60, 0.0f,
|
||||
0.0f, 0.0f, 0.0f, OverlapMode::Off, 0.0f, false, 2.0f);
|
||||
}
|
||||
SECTION("BoxSum border gradient") {
|
||||
CompareCpuVsGpu(IntegratorMode::BoxSum, std::nullopt, 4.0f, false, 60, 0.0f,
|
||||
0.0f, 0.0f, 0.0f, OverlapMode::Off, 0.0f, false, 2.0f);
|
||||
}
|
||||
SECTION("ProfileGaussian border gradient trim") {
|
||||
CompareCpuVsGpu(IntegratorMode::ProfileGaussian, std::nullopt, 0.0f, false, 60, 0.0f,
|
||||
0.0f, 0.0f, 0.0f, OverlapMode::Off, 0.0f, false, 2.0f);
|
||||
}
|
||||
// The radial background curvature correction is computed independently in the two engines
|
||||
// (host loop vs radial_correct kernel), so it needs its own parity coverage.
|
||||
SECTION("BoxSum radial") { CompareCpuVsGpu(IntegratorMode::BoxSum, std::nullopt, 4.0f, true); }
|
||||
|
||||
Reference in new issue
Block a user