-
Notifications
You must be signed in to change notification settings - Fork 45
Add spatial hashing #1169
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
Add spatial hashing #1169
Conversation
I attempted to stay close to the KD-Tree and BallTree API. However, the purpose of the SpatialHash class is to help locate the faces that a list of coordinates lie within. Because of this, the intent of the `query` function for the SpatialHash is a bit different than that for the KD and Ball trees. Additional support routines are provided for assessing whether a point is inside or outside a polygon. This is done by calculating the barycentric coordinates of a point in a convex polygon. The method is defined so that the sum of the barycentric coordinates is exactly one. Because of this, if any of the barycentric coordinates are negative, we immediately know that a point is outside the polygon. All coordinate calculations are done using (lon,lat) in radians for the SpatialHash class. Cartesian coordinates are not supported in this commit.
|
Check out this pull request on See visual diffs & provide feedback on Jupyter Notebooks. Powered by ReviewNB |
|
This looks great so far! May you add a |
philipc2
left a comment
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Can you add the spatial-hashing notebook here? (both in the outline and the toc tree at the bottom)
I'm thinking between "Subsetting" and "Cross-Sections?" would be a good spot.
https://github.com/UXARRAY/uxarray/blob/main/docs/userguide.rst?plain=1
Yes, I'll take care of both of these. |
* Ensure that the lon bounds are sorted from low to high. This is needed to make sure that the index looping for filling the hashtable actually executes. * All barycentric coordinates are calculated directly. Rather than calculating the last coordinate to ensure they sum to one, we now compute all coordinates. The coordinates are calculated now to align with the indexing of the node ID's so that np.sum(bcoords*nodes) returns the barycentric interpolation estimate of point. If the point is within the element, then the barycentric interpolation estimate matches the input coordinate (to machine precision). I've added this as a check.
|
@philipc2 - I've added tests for the spatial hashing, fixed formatting, and added spatial hashing to the toc in the userguide. Let me know if there's anything else you'd like to see updated |
philipc2
left a comment
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Looks great! A few small comments attached.
I'm going to play around with this today.
Thanks for putting this together so quickly!
Co-authored-by: Philip Chmielowiec <[email protected]>
philipc2
left a comment
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Some leftover print statements.
|
I'm having some issues with the It stalls for multiple minutes when trying to construct the tree. This was one of the grids that gave me some trouble in #1013 |
philipc2
left a comment
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Looks like one of the Github suggestions broke the pre-commit. Can you run it again?
Also, please restart and clear the outputs of the notebook, they will be rendered via our CI. Other than that all looks good.
I re-ran |
Oops, look's like its complaining about a merge conflict. |
Instead, we're favoring a check of the predicted coordinates using barycentric interpolation
Co-authored-by: Philip Chmielowiec <[email protected]>
Co-authored-by: Philip Chmielowiec <[email protected]>
philipc2
left a comment
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Thanks for this contribution! Other than the comments I left earlier, it looks good to me.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
This looks great! I will make use of the barycentric weights in one of my current PR's, so that is really helpful to me. Thanks for your contribution!
The denominator in the barycentric weights calculation (Weischell weights) is clipped to be no smaller than `ERROR_TOLERANCE` from the uxarray.constants module. This change is made to fix an issue, reported anectdotally by @Philip2c in UXARRAY#1169
When the denominator is clipped, rather than the individual triangle areas, the Weischell weights are incorrect for the case when a query point is on a face vertex. I've added tests for query points on edges and vertices
|
Turns out the issue with the It also appears we have a typo in our Lines 1386 to 1394 in d9f091f
I'll raise an issue and get this fixed. Glad to see that the issue wasn't anything with your implementation. |
|
🥳 - thanks @philipc2 and @aaronzedwick for your feedback. Without it, I would have not seen some of the cases that we ended up building tests for. This is great to see pushed across the finish line. Feel free to reach out on any future issues related to the spatial hashing. I'm happy to chip in. |
|
Thanks for this work and hoping to see few more features in future :) |
Closes #1126
Overview
This PR adds the
SpatialHashclass in theneighbors.pymodule. This class is used to encapsulate the necessary information and methods for conducting unstructured grid searches using spatial hashes. As part of the initialization of theSpatialHashobject, an associated unstructured grid is used to construct a uniformly spaced structured grid, called the "hash grid", and relate cell indices in the hash grid to elements in the unstructured grid. This hash table is a critical element of the spatial hash grid search as it is used to create a short-list of elements to search within.The
SpatialHash.querymethod returns the element id that a point (or element ids that a list of points) reside within alonside the barycentric coordinates. I've included helper methods to compute the barycentric coordinates of a point in relation to a given unstructured grid face (it works for convex faces n>=3 vertices). The barycentric coordinates are used to determine if a point is inside or outside a face; if all the barycentric coordinates are between [0,1], then a point is inside a face.Currently, only spherical coordinates (in radians or degrees) are supported for this search.
Expected Usage
PR Checklist
General
Testing
Documentation
_) and have been added todocs/internal_api/index.rstdocs/user_api/index.rstExamples
docs/examples/folderdocs/examples.rsttoctreedocs/gallery.ymlwith appropriate thumbnail photo indocs/_static/thumbnails/