-
Notifications
You must be signed in to change notification settings - Fork 11
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
Region definitions assume [0, 360] longitudes range #229
Comments
Returning to this now. It occurs to me that once this is implemented, there's no need to use Separately, we shouldn't modify the longitude values of the input data. So it's at the |
So we need to make some design choices about what Lines 151 to 154 in dded426
First, there is the obvious problem of things other than length-2 sequences being passed in. Of greater concern, currently the region will be silently empty if the two bounds are not in ascending order, given the logic in Lines 9 to 14 in dded426
If e.g. This is easy enough to fix in the current paradigm where longitudes are assumed to be [0, 360) both in the region definition and the input data, e.g. Suppose the region was defined with longitude bounds (-20, 10). If these get shifted to the 0-360 grid, they become (340, 10). So this will yield the empty region as just discussed. Sorting the longitudes also doesn't help, because then you've inverted the region: turning (340, 10) into (10, 340) makes the region span 330 degrees longitude (from 10E to 20W), rather than 30 degrees (from 20W to 10E) So perhaps the solution is to not shift the region definitions to the (0, 360) grid, and instead shift the input data's longitudes to whatever 360 degree interval on which the Region is defined. |
What if we went with the convention that the left value always represents the "western" boundary of the region and the right value always represents the "eastern" boundary? Essentially we would need to add logic internally to interpret things like (340, 10) as (340, 360) and (0, 10). I think you should shift the region definitions to whatever convention the underlying data uses (so in this example in the -180 to 180 convention, the region becomes simpler; it is just (-20, 10) in longitude). What do you have in mind for how to determine which longitude convention the underlying data uses? In simple cases, I think you could do it automatically (e.g. if data from the global domain is present), but in a limited domain setup where not all longitudes are represented (to be fair these use-cases are uncommon), you could run into ambiguities. A keyword argument (something like |
This is a fair point. We already have one user (@chuaxr) running limited domain. (And not even on a lon/lat grid, which points to a bigger issue we should tackle at some point of generalizing our coordinates. @chuaxr, have you been doing any regional averaging? If so, what do your Separately, even for global domains, we can't count on (0, 360) and (-180, 180) being the only ones, as some GFDL ocean models use (-280, 80). See e.g.
That's not a bad idea.
Whether or not the longitudes are global/cyclic, we can always unambiguously identify W. Hem. and E. Hem. points. If they are cyclic, then we should adapt regions to the grid accordingly. If not, then we'll have to check that the region is fully defined on the given grid, c.f. #230. So perhaps something like |
Good point! Yes, I think |
Just thought of an additional wrinkle: I still think that
While I'm at it, I'll add checks for Does that sound like a good idea? |
Yeah I like it; that sounds great! |
At the moment, the only Region I have defined is the whole domain. I mainly use this for the purpose of domain-averaged time-series. (As I recall, I ran into problems with the regular time series average trying to group by year.) domain = Region(
name='domain',
description='Entire domain',
lat_bounds=(-1,2), #larger than 0,1
lon_bounds=(-1,2), #larger than 0,1
do_land_mask=False
) Note that I do the following in my pre-processing function: ds.coords['lat']=('south_north',np.linspace(0,1,sn_size))
ds.coords['lon']=('west_east',np.linspace(0,1,we_size)) |
Thanks @chuaxr , that's helpful to know. Let us know if you come across the problem again you're referring to. |
@spencerahill I encountered the time-averaging problem within the last month, and used the domain region as a workaround. This is probably related to #252. |
I am considering a breaking change to make this more explicit: switch from Another consideration: As I mentioned above, at some point we probably want to generalize from the inherently lat-lon framework to be more general. Hard-coding in I'll go ahead with this approach unless anybody strongly objects. |
Yes, I like that idea; it shouldn't be too hard for me to modify things in my object library either. |
Just noticed this while using
Region.ts
on data that is on a [-180, 180] longitude grid, using the following region:The (342, 360) bit gets dropped, since it is out of the array's (-180, 180) range, causing the region to be truncated to (0, 40). This is physically incorrect and thus a bug.
We need to translate all region definitions and the longitude arrays on which the regional reductions are operating to a standard longitude array, which by convention should be either (-180, 180) or (0, 360). This can be accomplished by noting that
(0, 180) + 360*i
corresponds to the Eastern Hemisphere and(180, 360) + 360*j
corresponds to the Western hemisphere, wherei
andj
are integers. E.g.i=0, j=-1
corresponds to the (-180, 180) grid.So the steps would be
Once implemented, we should be able to support longitude arrays with arbitrary start and end values.
The text was updated successfully, but these errors were encountered: