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

🩹Fix for when the backsweep is a parameter rather than constant #1422

Merged
merged 5 commits into from
Jan 27, 2024

Conversation

jsnel
Copy link
Member

@jsnel jsnel commented Jan 27, 2024

The optimizer would crash

When setting the values in the model scheme from a constant to a parameter, the optimizer would crash with "Cannot determine Numba type of <class 'glotaran.parameter.parameter.Parameter'> " as it tried to use the parameter as a numeric value. Ultimately numba would complain as that's where the value would be first used.

Specifically: "glotaran\builtin\elements\kinetic\matrix.py", line 27

Note: This PR doesn't add a unit test (yet), but that should be added at the level of the optimizer since the element tests themselves work only with numeric definitions.

The optimizer would crash

When setting the values in the model scheme from a constant to a parameter, the optimizer would crash with "Cannot determine Numba type of <class 'glotaran.parameter.parameter.Parameter'> " as it tried to use the parameter as a numeric value. Ultimately numba would complain as that's where the value would be first used.

Specifically: `"glotaran\builtin\elements\kinetic\matrix.py", line 27`
Copy link
Contributor

Binder 👈 Launch a binder notebook on branch jsnel/pyglotaran/fix_staging/backsweep_period_parameter

Copy link
Contributor

@sourcery-ai sourcery-ai bot left a comment

Choose a reason for hiding this comment

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

PR Type: Bug fix

PR Summary: The pull request addresses an issue where the optimizer would crash when a parameter was used instead of a constant numeric value for the backsweep in the model scheme. The changes include a type check and assignment to handle the Parameter object correctly.

Decision: Comment

📝 Type: 'Bug fix' - not supported yet.
  • Sourcery currently only approves 'Typo fix' PRs.
✅ Issue addressed: this change correctly addresses the issue or implements the desired feature.
No details provided.
✅ Small diff: the diff is small enough to approve with confidence.
No details provided.

General suggestions:

  • Ensure that the Parameter object is always initialized with a value attribute to prevent potential runtime errors.
  • Consider using a getter method for accessing the value of the Parameter object to encapsulate the logic and provide a single point of maintenance.
  • Rename the boolean variable to include a prefix that indicates its nature, such as has_backsweep, to improve code readability.
  • Document the expected types of backsweep_period in the function's docstring or type annotations for better code clarity.

Thanks for using Sourcery. We offer it for free for open source projects and would be very grateful if you could help us grow. If you like it, would you consider sharing Sourcery on your favourite social media? ✨

Share Sourcery

Help me be more useful! Please click 👍 or 👎 on each comment to tell me if it was helpful.

@@ -172,6 +173,8 @@ def parameters(
scales = self.scale or [1.0] * nr_gaussians
backsweep = self.backsweep is not None
backsweep_period = self.backsweep if backsweep else 0
if isinstance(backsweep_period, Parameter):
backsweep_period = backsweep_period.value
Copy link
Contributor

Choose a reason for hiding this comment

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

issue (llm): Directly accessing the value attribute of a Parameter object could be risky if there's any chance the Parameter could be uninitialized or if the value attribute could be absent. It might be safer to use a getter method or to ensure that Parameter objects always have a value attribute.

Copy link

codecov bot commented Jan 27, 2024

Codecov Report

All modified and coverable lines are covered by tests ✅

Comparison is base (065ee43) 84.9% compared to head (3c4b3d2) 84.9%.

Additional details and impacted files
@@           Coverage Diff           @@
##           staging   #1422   +/-   ##
=======================================
  Coverage     84.9%   84.9%           
=======================================
  Files           91      91           
  Lines         3746    3746           
  Branches       728     728           
=======================================
  Hits          3182    3182           
  Misses         450     450           
  Partials       114     114           

☔ View full report in Codecov by Sentry.
📢 Have feedback on the report? Share it here.

@@ -172,6 +173,8 @@ def parameters(
scales = self.scale or [1.0] * nr_gaussians
backsweep = self.backsweep is not None
backsweep_period = self.backsweep if backsweep else 0
if isinstance(backsweep_period, Parameter):
Copy link
Member

Choose a reason for hiding this comment

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

Since Parameter implements __float__ we could simply change the assignment to

- backsweep_period = self.backsweep if backsweep else 0
+ backsweep_period = float(self.backsweep) if backsweep else 0

That way we also wouldn't need the type ignore in line 185

Copy link
Member Author

@jsnel jsnel Jan 27, 2024

Choose a reason for hiding this comment

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

Tried to adopt that suggestion ...

But:

glotaran\builtin\items\activation\gaussian.py:175: error: Argument 1 to "float" has incompatible type "Parameter | float | str | None"; expected "str | Buffer | SupportsFloat | SupportsIndex" [arg-type]
glotaran\builtin\items\activation\gaussian.py:183: error: Unused "type: ignore" comment [unused-ignore]

Copy link
Member

Choose a reason for hiding this comment

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

That said using a pydantic Model instead of dataclass for GaussianActivationParameters should also take proper care of type coercion.

Copy link
Member

Choose a reason for hiding this comment

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

That said using a pydantic Model instead of dataclass for GaussianActivationParameters should also take proper care of type coercion.

Since it is a drop in replacement, I have no objection to change it.

Copy link
Member

Choose a reason for hiding this comment

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

Tried to adopt that suggestion ...

But:

glotaran\builtin\items\activation\gaussian.py:175: error: Argument 1 to "float" has incompatible type "Parameter | float | str | None"; expected "str | Buffer | SupportsFloat | SupportsIndex" [arg-type]
glotaran\builtin\items\activation\gaussian.py:183: error: Unused "type: ignore" comment [unused-ignore]

This is limitation of mypy, since it cannot understand that the type is narrowed done at that point. Either ignore it or add an assert that is of float instance.

jsnel added 2 commits January 27, 2024 18:28
This is possible since Parameter implements __float__
@jsnel jsnel force-pushed the fix_staging/backsweep_period_parameter branch from 7d5e37c to b788092 Compare January 27, 2024 17:28
Copy link

Quality Gate Passed Quality Gate passed

Kudos, no new issues were introduced!

0 New issues
0 Security Hotspots
No data about Coverage
0.0% Duplication on New Code

See analysis details on SonarCloud

@jsnel
Copy link
Member Author

jsnel commented Jan 27, 2024

Verified the changes work

@jsnel jsnel merged commit 5f16090 into glotaran:staging Jan 27, 2024
21 of 33 checks passed
@jsnel jsnel deleted the fix_staging/backsweep_period_parameter branch January 27, 2024 18:07
jsnel pushed a commit that referenced this pull request Jan 27, 2024
…1423)

Just a small additional clean-up after #1422 to get rid of the backsweep boolean flag, which is a residual of the < 0.8 model syntax when we had this as user input.
jsnel added a commit to jsnel/pyglotaran that referenced this pull request Jun 2, 2024
…aran#1422)

* Fix for crashing optimizer when the backsweep is a parameter rather than constant

---------

Co-authored-by: s-weigand <s.weigand.phy@gmail.com>
jsnel pushed a commit to jsnel/pyglotaran that referenced this pull request Jun 2, 2024
…lotaran#1423)

Just a small additional clean-up after glotaran#1422 to get rid of the backsweep boolean flag, which is a residual of the < 0.8 model syntax when we had this as user input.
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.

3 participants