jiayuasu opened a new issue, #3256:
URL: https://github.com/apache/sedona/issues/3256

   ## Expected behavior
   
   Rasterization should have a documented, deterministic rule for deciding 
whether a stored double-precision geometry coordinate represents a pixel grid 
boundary. The rule should behave consistently across pixel scales and 
world-coordinate magnitudes, while preserving coordinates that genuinely cross 
a boundary by a representable positive distance.
   
   ## Actual behavior
   
   Grid-boundary handling currently depends on whether the computed inverse 
affine coordinate happens to be exactly integral as a `double`:
   
   ```java
   double pixel = (coordinate - origin) / scale;
   ```
   
   Common decimal and affine construction paths can leave a nonintegral residue 
for an intended boundary, causing an endpoint-only adjacent cell to be burned. 
Conversely, division can round a genuine adjacent-double crossing to an 
integral pixel coordinate, causing a cell with positive-length overlap to be 
omitted.
   
   Examples:
   
   - Decimal grid: `(0.3 - 0.6) / -0.1 == 2.9999999999999996`.
   - Affine-generated value: with origin `0.1` and scale `0.1`, `0.1 + 2 * 0.1 
== 0.30000000000000004`, and the inverse result is `2.0000000000000004`.
   - Large origin: `(1000000.03 - 1000000.0) / 0.01 == 3.0000000027939677`.
   - Rounded quotient in the other direction: `0.030000000000000002 / 0.01 == 
3.0`, even though the coordinate is the next representable double above `0.03`.
   
   ## Steps to reproduce
   
   ### Intended decimal boundary is classified as nonintegral
   
   ```sql
   SELECT RS_BandAsArray(
     RS_AsRaster(
       ST_GeomFromWKT('LINESTRING (0.22 0.22, 0.3 0.3)'),
       RS_MakeEmptyRaster(1, 'B', 6, 6, 0.0, 0.6, 0.1, -0.1, 0.0, 0.0, 0),
       'B', true, 1.0, 0.0, false),
     1);
   ```
   
   Under a policy that accepts the decimal relation as a boundary, the segment 
traverses only zero-based `(row 3, column 2)` and terminates at the pixel 
corner. The inverse-coordinate residue additionally burns endpoint-only `(row 
2, column 2)`. Under an exact stored-IEEE policy, that tiny extension would 
instead be considered real; choosing between those interpretations is the 
decision this issue requests.
   
   ### Genuine representable crossing is classified as integral
   
   ```sql
   SELECT RS_BandAsArray(
     RS_AsRaster(
       ST_GeomFromWKT('LINESTRING (0.025 0.045, 0.030000000000000002 0.045)'),
       RS_MakeEmptyRaster(1, 'B', 6, 6, 0.0, 0.06, 0.01, -0.01, 0.0, 0.0, 0),
       'B', true, 1.0, 0.0, false),
     1);
   ```
   
   `0.030000000000000002` is the next representable double above `0.03`, so the 
line enters column 3 for a positive distance. Sedona burns only zero-based 
`(row 1, column 2)` because the inverse division rounds the endpoint to exactly 
`3.0`; zero-based `(row 1, columns 2 and 3)` should be burned under exact 
stored-double geometry.
   
   ## Why a tolerance is not a complete fix
   
   The original source intent is no longer available after parsing or 
coordinate transformation. For origin `0.1`, scale `0.1`, and boundary index 
`2`:
   
   ```text
   decimal boundary                         = 0.3
   binary affine result (0.1 + 2 * 0.1)    = 0.30000000000000004
   Math.nextUp(0.3)                        = 0.30000000000000004
   ```
   
   The same stored bits can mean either an affine-generated boundary or a 
genuine one-double crossing beyond the decimal boundary. No epsilon can recover 
those two intents. A fixed or magnitude-scaled tolerance can also swallow real 
endpoint slivers, while unconditional exact-decimal arithmetic can add 
per-vertex allocation and CPU cost.
   
   ## Decision required
   
   Choose and document the boundary-equivalence policy before implementing it. 
Candidate policies include:
   
   1. one canonical boundary encoding produced by the raster's actual forward 
affine transform;
   2. an explicit finite set of boundary-equivalent encodings, such as 
forward-affine and canonical-decimal relations;
   3. exact arithmetic over the stored IEEE-754 values, accepting that common 
decimal relations may not be boundaries.
   
   This is a compatibility policy, not recovery of source intent. If multiple 
encodings are accepted, adjacent doubles may deliberately be 
boundary-equivalent and that exception must be documented.
   
   ## Acceptance criteria
   
   - Public documentation defines which stored coordinate encodings are treated 
as grid boundaries.
   - Classification is axis-local, direction-independent, and consistent across 
unit, decimal, fractional, negative-scale, and large-origin grids.
   - Values not in the accepted equivalence set preserve their exact 
mathematical side; quotient rounding alone is not an equality decision.
   - Tests cover decimal literals, coordinates produced by the raster's actual 
affine operation, `1/3`-style scales, large origins, bottom-up rasters, and 
adjacent `Math.nextDown`/`Math.nextUp` values.
   - Tests explicitly document the unavoidable `0.3` versus 
`0.30000000000000004` policy choice.
   - The proposed implementation includes benchmark results for long LineString 
and Polygon workloads against PR #3251, with any accepted regression limit 
stated explicitly.
   - Clipped endpoints carry explicit boundary/side provenance from the clipper 
rather than being reclassified solely from rounded coordinates. #3255 should be 
implemented first.
   
   ## Related work
   
   - #3120 tracks the exact-grid-vertex case; #3251 fixes it when the computed 
pixel coordinate is already exactly integral.
   - #3255 should land first so synthetic clipped endpoints do not lose their 
boundary provenance.
   
   ## Settings
   
   - Sedona version: PR #3251 head `72d9cc26541` / `2.0.0-SNAPSHOT`
   - API type: SQL and Java
   - JRE: 17
   - Environment: local development checkout
   
   I searched open and closed issues and did not find a duplicate.
   


-- 
This is an automated message from the Apache Git Service.
To respond to the message, please log on to GitHub and use the
URL above to go to the specific comment.

To unsubscribe, e-mail: [email protected]

For queries about this service, please contact Infrastructure at:
[email protected]

Reply via email to