Skip to content

Add geodetic representations - #11086

Merged
astrojuanlu merged 22 commits into
astropy:masterfrom
astrojuanlu:geodetic-representations
Dec 29, 2020
Merged

astrojuanlu merged 22 commits into
astropy:masterfrom
astrojuanlu:geodetic-representations

Conversation

@astrojuanlu

Copy link
Copy Markdown
Member

Description

In line with discussions at #4261, this pull request aims to add geodetic representations.

I started with WGS84GeodeticRepresentation to touch base and get a few eyes on my approach. In particular, I don't think we can cleanly have a generic GeodeticRepresentation where the ellipsoid is an extra parameter, retained in roundtrip transformations, but I would be glad to be proven wrong.

The tests are almost a copy-paste of TestSphericalRepresentation, with a few changes:

  • height instead of distance
  • height can only be a Quantity, not a Distance
  • I didn't add differentials (not sure if worth it)

Besides, I also adapted test_gc2gd and test_gd2gc from test_earth.py to make sure we get the same results.

@mhvk mhvk left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

@astrojuanlu - this looks good! I'm actually pleasantly surprised to see how relatively simple it is to add - the work is mostly in the tests!

Beyond the small in-line comments: I think these representations belong in earth.py as they are not useful as general representations. Similarly, I'd put the tests in test_earth. (Or perhaps a new earth_representations or even an earth/ module. Though seems a bit overkill right now.)

I agree that for now we can ignore velocities - we can add the ability to mimic observations from airplanes when the need arises!

How were you thinking of proceeding? A first step might simply be to remove the transformation machinery in EarthLocation and instead go through these representations inside from_geodetic and lon, lat, heigh - to_geodetic() may need some kind of deprecation warning as right now it returns a namedtuple and people may count on it. (I think that is OK, we should move to .represent_as anyway, making it more frame-like.)

p.s. I'll change this to draft right now just to be sure we don't accidentally merge.

Comment thread astropy/coordinates/representation.py Outdated
Comment thread astropy/coordinates/representation.py Outdated
Comment thread astropy/coordinates/representation.py Outdated
Comment thread astropy/coordinates/representation.py Outdated
@mhvk
mhvk marked this pull request as draft November 25, 2020 15:07
@astrojuanlu

Copy link
Copy Markdown
Member Author

Thanks for the prompt review @mhvk !

I agree with moving this to earth.py and with all your comments. I wanted to think about the way forward with EarthLocation today but I couldn't, so I don't have any ideas yet - will give it some thought tomorrow.

@mkbrewer

Copy link
Copy Markdown
Contributor

I agree that for now we can ignore velocities - we can add the ability to mimic observations from airplanes when the need arises!

Don't forget balloons! https://askdrphilastro.wordpress.com/2019/12/15/blast-antarctica-2019-2020/

@mhvk

mhvk commented Nov 27, 2020

Copy link
Copy Markdown
Contributor

Don't forget balloons!

How can I forget my own colleague! So, we will have to get there...

@astrojuanlu
astrojuanlu force-pushed the geodetic-representations branch from 6b09266 to b227ed9 Compare November 30, 2020 10:18
@astrojuanlu astrojuanlu added this to the v4.3 milestone Nov 30, 2020
@astrojuanlu
astrojuanlu force-pushed the geodetic-representations branch from b227ed9 to e831960 Compare November 30, 2020 10:23
Comment thread astropy/coordinates/tests/test_earth.py Outdated
@astrojuanlu

Copy link
Copy Markdown
Member Author

Addressed the first batch of comments, going to look into EarthLocation now.

@astrojuanlu

Copy link
Copy Markdown
Member Author

What I did in the end was to deprecate .to_geodetic and .to_geocentric without changing their return values, and added a new .represent_as.

This is ready for a second pass!

@astrojuanlu
astrojuanlu requested a review from mhvk November 30, 2020 12:40
@astrojuanlu

Copy link
Copy Markdown
Member Author

Many test failures due to the AstropyDeprecationWarning I introduced - I guess no internal calls to deprecated methods are allowed. Will fix it.

@mkbrewer

mkbrewer commented Nov 30, 2020 •

Copy link
Copy Markdown
Contributor

I would just note that many locations on Earth have heights that are below that of the ellipsoid. I seems a bit unreasonable to force a different method for creating an EarthLocation in these instances.

@mhvk

mhvk commented Nov 30, 2020

Copy link
Copy Markdown
Contributor

Darn, we'd need allow_negative. I think for now it would be best to just proceed with a Quantity - we can deal with insisting it is a length differently/later.

@mhvk mhvk left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

@astrojuanlu - this is starting to look very nice. Bit of a mix of larger and probably overly detailed comments.

More general one is where we stop. One option is actually a bit before where you are now, i.e., not add deprecation messages yet, but just introduce the new representations and use them internally only for the transformations. This has the advantage that no tests will fail yet. Arguably, in that case, we would also not yet add the represent_as method (which is not tested yet, so that is fine, I think).

The other is perhaps a bit further than you are now, whether EarthLocation stops becoming a Quantity and instead stores the representation in .data like a frame (or perhaps as an intermediate suggestion still shares the data with a CartesianRepresentation).

But my sense would be to take the smaller step suggested above, so we can get this in and follow-up on it.

Comment thread astropy/coordinates/earth.py Outdated
For the conversion to geodetic coordinates, the ERFA routine
``gc2gd`` is used. See https://github.com/liberfa/erfa
"""
warn("Method .to_geodetic(ellipsoid) is deprecated, "

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

Agree with the deprecation message, but in analogy with a frame or sky coord, I think there is little against still having the properties for particular representations, i.e., I think we should allow (and also refer to in the warning message),

el.{wgs84,...}geodetic
el.cartesian

Copy link
Copy Markdown
Member Author

Choose a reason for hiding this comment

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

Removed the deprecation message for now, but saving this for the future.

Comment thread astropy/coordinates/earth.py Outdated
llh.lat,
u.Quantity(llh.height, self.unit, copy=False))

def represent_as(self, other_class):

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

Again seeing EarthLocation as more like a frame/skycoord rather than a representation, I think we can allow strings. I'd suggest following the nomenclature in their represent_as method and calling it base.

Copy link
Copy Markdown
Member Author

Choose a reason for hiding this comment

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

Removed represent_as for now, but saving this for the future.

Comment thread astropy/coordinates/earth.py Outdated
Comment thread astropy/coordinates/earth.py Outdated
return new_array.view(self.dtype).reshape(self.shape)


class BaseGeodeticRepresentation(BaseRepresentation):

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

I think this will get registered in REPRESENTATION_CLASSES, which is not ideal... Pinging @adrn for ideas; should we allow a name = False explicit way to avoid registration? (Note: this should not have to hold up this PR!)

Comment thread astropy/coordinates/earth.py Outdated
Comment thread astropy/coordinates/tests/test_earth.py Outdated
Comment thread astropy/coordinates/tests/test_earth.py Outdated
assert str(greenwich.info).startswith('name = Royal Observatory Greenwich')


class TestWGS84GeodeticRepresentationRepresentation:

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

I would shrink this class substantially - many of the tests are done on Spherical to just have them done once, no need to do them again. Also, do re-align for the longer name...

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

Thinking more, since all new tests are (very nicely) just focussed on the representations, how about a new test_geodetic_representations?

Copy link
Copy Markdown
Member Author

Choose a reason for hiding this comment

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

I moved these tests to test_geodetic_representations.py, but I'm not sure which ones to remove.

Comment thread astropy/coordinates/tests/test_earth.py Outdated
Comment thread astropy/coordinates/tests/test_earth.py Outdated
@astrojuanlu

Copy link
Copy Markdown
Member Author

But my sense would be to take the smaller step suggested above, so we can get this in and follow-up on it.

I agree - I will remove the deprecation warnings and remove represent_as for now, and follow up in a future PR. Addressing your comments now.

@astrojuanlu
astrojuanlu force-pushed the geodetic-representations branch from 0a95f85 to 988b8fe Compare December 1, 2020 09:27
@astrojuanlu
astrojuanlu marked this pull request as ready for review December 1, 2020 09:30
@mkbrewer

mkbrewer commented Dec 2, 2020

Copy link
Copy Markdown
Contributor

While supporting alternate ellipsoids is fine, you should realize that there is more work involved in doing so. As currently written, ErfaAstrom.apco() calls erfa.apco() which calculates the observer's position and velocity based on the WGS-84 ellipsoid. Thus geodetic coordinates based on an alternate ellipsoid will yield incorrect results in any ICRS<->CIRS or ICRS<->AltAz transform.

@mkbrewer

mkbrewer commented Dec 2, 2020

Copy link
Copy Markdown
Contributor

I should note that this relates to task 1) in issue #11072

@astrojuanlu

Copy link
Copy Markdown
Member Author

Warnings are legitimate:

/home/docs/checkouts/readthedocs.org/user_builds/astropy/envs/11086/lib/python3.8/site-packages/astropy/coordinates/earth.py:docstring of astropy.coordinates.GRS80GeodeticRepresentation:1: WARNING: py:class reference target not found: astropy.coordinates.earth.BaseGeodeticRepresentation
writing output... [ 16%] api/astropy.coordinates.SphericalCosLatDifferential .. api/astropy.io.ascii.Latex
/home/docs/checkouts/readthedocs.org/user_builds/astropy/envs/11086/lib/python3.8/site-packages/astropy/coordinates/earth.py:docstring of astropy.coordinates.WGS72GeodeticRepresentation:1: WARNING: py:class reference target not found: astropy.coordinates.earth.BaseGeodeticRepresentation
/home/docs/checkouts/readthedocs.org/user_builds/astropy/envs/11086/lib/python3.8/site-packages/astropy/coordinates/earth.py:docstring of astropy.coordinates.WGS84GeodeticRepresentation:1: WARNING: py:class reference target not found: astropy.coordinates.earth.BaseGeodeticRepresentation
...
[changelog_links] Adding changelog links to "changelog"
<rst_epilog>:14: WARNING: py:class reference target not found: astropy.coordinates.earth.BaseGeodeticRepresentation

fixing

@mhvk
mhvk force-pushed the geodetic-representations branch from 783303e to 8226e48 Compare December 29, 2020 00:01
@mhvk
mhvk force-pushed the geodetic-representations branch from 8226e48 to 4612ca1 Compare December 29, 2020 00:09
@mhvk

mhvk commented Dec 29, 2020

Copy link
Copy Markdown
Contributor

@astrojuanlu - OK, I also changed the tests now. Plus one thing that you should sign off on: to make ELLIPSOIDS a dict with the actual representations as values. I think it works quite nicely, mostly because #11090 already replaced the meta class with __init_subclass__, so one can now easily chain things. See 4612ca1.

@mhvk mhvk left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

Approving, but, as noted, @astrojuanlu, would be best if you approve the changes I made!

'lat': Latitude,
'height': u.Quantity}

def __init_subclass__(cls, **kwargs):

Copy link
Copy Markdown
Member Author

Choose a reason for hiding this comment

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

Nice trick!

@astrojuanlu astrojuanlu left a comment

Copy link
Copy Markdown
Member Author

Choose a reason for hiding this comment

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

Can't approve my own pull request. This looks good to me, thanks @mhvk for the final tweaks!

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Projects

None yet

Development

Successfully merging this pull request may close these issues.

3 participants