Skip to content

adding average_radius parameter into the rotation wrapper #534

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Merged
merged 8 commits into from
Jan 20, 2025
Merged

Conversation

dkazanc
Copy link
Collaborator

@dkazanc dkazanc commented Dec 11, 2024

This PR should be used together with the vocentering branch of httomolibgpu.
The changes include adding a new parameter average_radius into the rotation wrapper in order to perform averaging of multiple sinograms to improve SNR and therefore CoR estimation accuracy.

Checklist

  • I have added tests that prove my fix is effective or that my feature works
  • New and existing unit tests pass locally with my changes
  • I have made corresponding changes to the documentation

Copy link
Collaborator

@yousefmoazzam yousefmoazzam left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

After mulling this over for a bit, I think there could be a way to test this more thoroughly.

If I understand the added logic correctly (and please do correct me if I've got things wrong), there are 4 cases:

  1. the average_radius parameter isn't provided to the method; the method wrapper sets average_radius=0, and thus the underlying method function should be given a non-averaged sinogram
  2. the average_radius parameter is provided to the method
  • the value is 0: the underlying method function should be given a non-averaged sinogram
  • the value is non-zero but within range: the underlying method function should be given an averaged sinogram, based on the block data and the value of average_radius
  • the value is non-zero and out of range: an error should be raised

The last case seems to be tested, but the other 3 cases aren't.

A non-averaged sinogram vs. an averaged sinogram that came from averaging n specific sinograms are distinguishable (ie, they should produce the exact same array). To test the other three cases, I think that one could write the dummy method function that is imported to assert on the array that is passed to it, like this test for example:

class FakeModule:
def fake_method(array):
np.testing.assert_array_equal(array, 42)
return array
mocker.patch(
"httomo.method_wrappers.generic.import_module", return_value=FakeModule
)
wrp = make_method_wrapper(
make_mock_repo(mocker),
"mocked_module_path",
"fake_method",
MPI.COMM_WORLD,
make_mock_preview_config(mocker),
)
dummy_block.data[:] = 42
wrp.execute(dummy_block)

For each test case, one could determine the sinogram that is expected to be extracted by the wrapper (non-averaged or averaged depending on the value of average_radius) and assert that the method function gets given this expected sinogram when the wrapper is called.

@dkazanc
Copy link
Collaborator Author

dkazanc commented Jan 20, 2025

@yousefmoazzam I've added two more tests, as you suggested above, so those situations are covered now :

  1. the value is 0: the underlying method function should be given a non-averaged sinogram
  2. the value is non-zero but within range: the underlying method function should be given an averaged sinogram, based on the block data and the value of average_radius
  3. the value is non-zero and out of range: an error should be raised

The tweaks are the following:
- the "index" value was unnecessarily defined both inside and outside
  the dummy method function with the same value: moved this to a single
  variable
- the expected data to be passed into the dummy method function was
  defined inside the dummy method function itself: moved this to be
  defined outside of the dummy method function for clarity
- the `original_array` variable was unnecessarily defined both inside
  and outside the dummy method function, with the same value: moved this
  to a single variable
- the `original_array` value was unnecessarily copied: removed the use
  of `copy()`
@yousefmoazzam
Copy link
Collaborator

yousefmoazzam commented Jan 20, 2025

Thanks for the updates!

Don't worry about IRIS CI failing, it's the flakey cupy import error once more... I ran the tests locally and they're all passing, so that's fine.

I made a few tweaks to the tests that I think makes them a bit clearer, where the first commit's message explains the changes. I also added a test for the last missing case (number 1. in my post above) where I think we want the method wrapper to implicitly set the average_radius to 0 if a value for that parameter isn't passed in.

Let me know if what I changed/added makes sense to you (am happy to rollback what I did if there's issues).

@dkazanc
Copy link
Collaborator Author

dkazanc commented Jan 20, 2025

thanks @yousefmoazzam , yes the changes make sense and the new test as well. I'll merge the PR and do the release of the backends as well.

@dkazanc dkazanc merged commit 46ca7e9 into main Jan 20, 2025
2 of 3 checks passed
@dkazanc dkazanc deleted the vocentering branch January 20, 2025 12:34
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

2 participants