Skip to content
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

Polarization/asymmetry function #97

Open
wants to merge 10 commits into
base: main
Choose a base branch
from
Open

Conversation

esmith1729
Copy link
Contributor

@pull-request-size pull-request-size bot added size/L and removed size/M labels Feb 5, 2025
@esmith1729 esmith1729 linked an issue Feb 6, 2025 that may be closed by this pull request
5 tasks
@esmith1729 esmith1729 changed the title Initial polarization func and test Polarization/asymmetry function Feb 6, 2025
Copy link
Contributor

@Tom-Willemsen Tom-Willemsen left a comment

Choose a reason for hiding this comment

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

Most of these things are relatively minor - core implementation looks good.

@@ -120,6 +120,50 @@ async def sum_spectra_with_wavelength(
return sum_spectra_with_wavelength


def polarization(a: sc.Variable, b: sc.Variable) -> sc.Variable:
Copy link
Contributor

Choose a reason for hiding this comment

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

Sorry this is my fault as I specified precisely this, but thinking more I think the signature is better expressed as sc.typing.VariableLike (actual types unchanged, it just means pyright will be happy for us to use sc.DataArray and others too in future). Again actual types don't change, just the type hints in the signature.

Comment on lines +136 to +137
On SANS instruments e.g. LARMOR, A and B correspond to intensity in different DAE
periods (before/after switching a flipper)
Copy link
Contributor

Choose a reason for hiding this comment

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

Suggested change
On SANS instruments e.g. LARMOR, A and B correspond to intensity in different DAE
periods (before/after switching a flipper)
On SANS instruments e.g. LARMOR, A and B correspond to intensity in different DAE
periods (before/after switching a flipper) and the output is interpreted as a neutron polarization ratio

On SANS instruments e.g. LARMOR, A and B correspond to intensity in different DAE
periods (before/after switching a flipper)
Or reflectometry instruments e.g. POLREF, the situation is the same as on LARMOR
On muon instruments, A and B correspond to measuring from different detector banks
Copy link
Contributor

Choose a reason for hiding this comment

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

Suggested change
On muon instruments, A and B correspond to measuring from different detector banks
On muon instruments, A and B correspond to measuring from forward/backward detector banks, and the output is interpreted as a muon asymmetry

("a", "b", "variance_a", "variance_b", "expected_value", "expected_uncertainty"),
[
# Case 1: Symmetric case with equal uncertainties
(5.0, 3.0, 0.1, 0.1, 0.25, 0.05762215285808055), # comment where tf this number came from
Copy link
Contributor

Choose a reason for hiding this comment

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

comment where tf this number came from

good idea

@pytest.mark.parametrize(
("a", "b", "variance_a", "variance_b", "expected_value", "expected_uncertainty"),
[
# Case 1: Symmetric case with equal uncertainties
Copy link
Contributor

Choose a reason for hiding this comment

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

What does "symmetric" mean here?

# Case 2: Asymmetric case with different uncertainties
(10.0, 6.0, 0.2, 0.3, 0.25, 0.04764984588117782),
# Case 3: Case with larger values and different uncertainty magnitudes
(100.0, 60.0, 1.0, 2.0, 0.25, 0.0120017902310447),
Copy link
Contributor

Choose a reason for hiding this comment

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

In our chat we also had some "simple" example cases - the sort which could be worked out easily "in your head". Those would make good test cases to add here.

Comment on lines +956 to +957
var_a = sc.Variable(dims=[], values=a, variances=variance_a, unit="", dtype="float64")
var_b = sc.Variable(dims=[], values=b, variances=variance_b, unit="", dtype="float64")
Copy link
Contributor

Choose a reason for hiding this comment

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

From https://scipp.github.io/generated/classes/scipp.Variable.html#scipp.Variable:

This constructor is meant primarily for internal use. Use one of the Specialized creation functions instead. See in particular scipp.array() and scipp.scalar().

(scalar is what you want here) - it still gives you a sc.Variable object in the end though.

polarization(var_a, var_b)


# test cases uncert = 0
Copy link
Contributor

Choose a reason for hiding this comment

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

?

@pytest.mark.parametrize(
("a", "b", "variances_a", "variances_b", "expected_values", "expected_uncertainties"),
[
# Case 1: Symmetric case with equal uncertainties
Copy link
Contributor

Choose a reason for hiding this comment

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

Not sure what "symmetric" means here - could you clarify?

Also the equal uncertainties seems not true.

Copy/paste?

Comment on lines +262 to +277
Polarization refers to the property of transverse waves which specifies the geometrical orientation of the
oscillations.

The polarization funtion provided will calculate the polarization between two values, A and B, which
have different definitions based on the instrument context.

Instrument-Specific Interpretations
SANS Instruments (e.g., LARMOR)
A: Intensity in DAE period before switching a flipper.
B: Intensity in DAE period after switching a flipper.

Reflectometry Instruments (e.g., POLREF)
Similar to LARMOR, A and B represent intensities before and after flipper switching.

Muon Instruments
A and B refer to Measurements from different detector banks.
Copy link
Contributor

Choose a reason for hiding this comment

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

I think we need to re-word this section a bit. Not your fault, this is kind of specific science knowledge here - which I'm no expert on myself but have picked up bits & pieces from talking to scientists.

How about something like:

Polarization/asymmetry

ibex_bluesky_core provides a helper method,
{py:obj}ibex_bluesky_core.devices.simpledae.reducers.polarization, for calculating the quantity (a-b)/(a+b). This quantity is used, for example, in neutron polarization measurements, and in calculating asymmetry for muon measurements.

For this expression, scipp's default uncertainty propagation rules cannot be used as the uncertainties on (a-b) are correlated with those of (a+b) in the division step - but scipp assumes uncorrelated data. This helper method calculates the uncertainties following linear error propagation theory, using the partial derivatives of the above expression.

The partial derivatives are:
[INSERT MATHS HERE - and see the fitting models docs pages for how to render nice maths equations in docs]
Which then means the variances computed by this helper function are:
[INSERT MATHS HERE]

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
Projects
None yet
Development

Successfully merging this pull request may close these issues.

Polarization/asymmetry
2 participants