Repository navigation
add imshow_simple_norm - #19623
add imshow_simple_norm#19623
Conversation
|
Thank you for your contribution to Astropy! 🌌 This checklist is meant to remind the package maintainers who will review this pull request of some common things to look for.
|
neutrinoceros
left a comment
There was a problem hiding this comment.
Hi Erik ! welcome to the astropy project, we hope you'll enjoy the contribution process !
| fig.colorbar(im) | ||
| """ | ||
| if ax is None: | ||
| if not HAS_MATPLOTLIB: |
There was a problem hiding this comment.
why not move the import dance a the top level of the function ?
There was a problem hiding this comment.
This was just following from the above - but I think the motivation is that it's possible (albiet unlikely) that the user might pass in an ax object that is not from matplotlib but some matplotlib look-alike. And in that case we might as well try instead of erroring out. But if they give None we have to have plt to do plt.gca()
So I'd rather not change it since it is addressing a conceivable (albiet unlikely) use case.
There was a problem hiding this comment.
we might as well try instead of erroring out
I think this hits close to a point I fundamentally disagree with. As a user, I much prefer my tools to say "sorry, I don't know what to do with this", than getting some uncontrolled error message nobody actually thought about later on.
But, you have status quo on your side, and there's no point making this function acting different than the rest of the API, so I won't push for it. Just wanted to highlight this one philosophical point of friction.
There was a problem hiding this comment.
(anecdoctally, I think we, as a community, effectively trained users to see any traceback as a question mark (is this a bug, or it is just not supported ?), to the point I've seen people reporting NotImplementedErrors, asking if they found a bug, or if they could somehow work around it)
There was a problem hiding this comment.
I'm not sure I agree with your broader point, but I'm not sure I disagree - that is, it's definitely a good point I'm just not sure how to balance the two conflicting desires/concerns. That said, I think, as you pointed out, this is a problem shared with the other function, so I'd rather we discuss this in a separate follow-on PR/issue (ideally after feature freeze! Since its been there for several years I think there's little harm in waiting another 6 mo to fix/change this)
There was a problem hiding this comment.
oh I can definitely get behind this plan ! I don't mean to block this, I'm just treating it as an opportunity to discover what hidden (to me) corners of astropy have in store
| "want that." | ||
| ) | ||
|
|
||
| imshow_kwargs = dict(kwargs) |
There was a problem hiding this comment.
better reflects what I think is the intention here
| imshow_kwargs = dict(kwargs) | |
| imshow_kwargs = kwargs.copy() |
| "want that." | ||
| ) | ||
|
|
||
| imshow_kwargs = dict(kwargs) |
There was a problem hiding this comment.
actually why even bother with a copy ? this dict is owned by the function, we can mutate it as needed
There was a problem hiding this comment.
It's because the next few lines split up the kwargs between snorm_kwargs and imshow_kwargs, and I felt it was confusing to leave one with just the name kwargs. And once I'm doing that it seemed better to keep kwargs itself pristine, and to me the dict(kwargs) construct better reflects the intention of "creating a new dictionary with a different purpose, but starting out with the same content as kwargs until we start popping things from it a few lines below".
That said, I guess the following would be equivalent as long as no one changes this in the future to use kwargs below:
| imshow_kwargs = dict(kwargs) | |
| imshow_kwargs = kwargs |
and is like a few microseconds more performant 🤷 . I'm fine with it either way so whoever ends up merging I'm comfortable with them either applying the change above or not as they like.
| imshow_kwargs["norm"] = SimpleNorm(**snorm_kwargs)(data) | ||
| imshow_result = ax.imshow(data, **imshow_kwargs) | ||
|
|
||
| return imshow_result, imshow_kwargs["norm"] |
There was a problem hiding this comment.
returning a dataclass instance would make it instantly clearer how to access which part. And if you absolutely need or want the tuple interface (mostly, unpacking ?), you could use a NamedTuple instead.
There was a problem hiding this comment.
I disagree. I think it is more important that this function is consistent with imshow_norm above (an existing implementation not added by this PR).
There was a problem hiding this comment.
making return values into NamedTuple would be backward compatible and can easily be made consistently throughout the API. Though, if it's a consistency issue, better to stick with what you have for this PR. What do you guys think of moving to NamedTuples later ?
There was a problem hiding this comment.
NamedTuple should be discussed as a new issue. Ultimately, as long as the changes here are consistent with existing implementation, I think it should be acceptable unless it is a bug. Thanks, all!
| return imshow_result, imshow_kwargs["norm"] | ||
|
|
||
|
|
||
| def imshow_simple_norm(data, ax=None, **kwargs): |
There was a problem hiding this comment.
none of the arguments are easy to annotate, but the return value is, and that's very useful in itself
There was a problem hiding this comment.
Unfortunately, this is not as clean as one would like because I would need to import matplotlib to include the full annotation which triggers all the optional dependency annoyances. But I did add just tuple which is better than nothing!
There was a problem hiding this comment.
for reference, this is how you do it for a type-only import
from typing import TYPE_CHECKING
if TYPE_CHECKING:
from matplotlib import MyType
def foo() -> "MyType": ...the reason this works is that typing.TYPE_CHECKING is exactly False at runtime, but the standard specifies that type checkers treat it as True.
|
|
||
|
|
||
| @pytest.mark.skipif(not HAS_PLT, reason="requires matplotlib") | ||
| def test_imshow_simple_norm(): |
There was a problem hiding this comment.
looks like 3 image tests in a trench coat to me
There was a problem hiding this comment.
I think it is fine as long as it passes?
There was a problem hiding this comment.
Yeah, I was just following the other test like this - I think at the time the sub-package maintainers (which was I think @larrybradley and someone else?) preferred it that way for the convenience functions. I'm not against changing that, but I'd prefer to defer it to later when it can be done for the rest of the tests in the sub-pagcakge.
There was a problem hiding this comment.
My issue is that, in their current form, I can't really say that these test actually check the output. Without changing the entire nature of the test, adding a couple more assertions would already help.
There was a problem hiding this comment.
@eteq To get this in before feature freeze, could you add a few more assertions?
There was a problem hiding this comment.
Point taken, done in the last commit! Probably would make sense to port those tests back to simple_imshow but I think that's not this PR so as not to mix cocnerns.
Co-authored-by: P. L. Lim <[email protected]> Co-authored-by: Erik Tollerud <[email protected]>
|
I believe the last couple of commits addressed all the comments (@neutrinoceros may not entirely agree but I think we're on the same page of "not critical so could be addressed in a PR after feature freeze to let this get in today) |
larrybradley
left a comment
There was a problem hiding this comment.
Thanks, @eteq. We can address the followup issues after feature freeze.
|
I opened #19635 as follow-up. Hopefully I didn't miss anything. Feel free to correct if I did. Thanks, all! |
Description
This PR adds a function @larrybradley and I discussed in the hazy distant past when
imshow_normwas first made: a convenient version of it that usessimple_norm's interface instead ofImageNormalizedirectly. The gist is that this allows a convenient and compact specification of imshow like this:which makes imports more compact for simple quick-viz cases.