blob: b04036fce0762ae0a4b51964866463dd590e585b [file] [view]
<!--
Licensed to the Apache Software Foundation (ASF) under one
or more contributor license agreements. See the NOTICE file
distributed with this work for additional information
regarding copyright ownership. The ASF licenses this file
to you under the Apache License, Version 2.0 (the
"License"); you may not use this file except in compliance
with the License. You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing,
software distributed under the License is distributed on an
"AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
KIND, either express or implied. See the License for the
specific language governing permissions and limitations
under the License.
-->
# Box2D Functions
The `Box2D` type in Sedona represents a planar axis-aligned bounding box — a rectangle described by four `Double` values: `xmin`, `ymin`, `xmax`, `ymax`. It is a first-class SQL type backed by a Spark UDT and serialises to a struct of four non-nullable doubles, so columns of `Box2D` round-trip natively through Parquet and align with GeoParquet 1.1 bbox covering columns.
`Box2D` complements the [Geometry](../Geometry-Functions.md) and [Geography](../geography/Geography-Functions.md) types. Use it when you need a compact, comparable bounding rectangle — for example, as a covering column on a GeoParquet table that lets the reader prune row groups, or as the join key in a spatial join that only needs an envelope-level match.
## Semantic notes
- `Box2D` values use closed-interval semantics: edge-touching boxes are considered intersecting and (per [ST_Contains](../Predicates/ST_Contains.md)) contained.
- Absence is represented by SQL `NULL` rather than an in-band sentinel.
- Bounds are required to be ordered (`xmin <= xmax`, `ymin <= ymax`). Inverted-bound values are reserved for a future antimeridian-wraparound semantics on geography bboxes; predicates and join planning throw `IllegalArgumentException` on inverted input today.
- Unlike [ST_Envelope](../Bounding-Box-Functions/ST_Envelope.md), which returns the envelope as a `Geometry` (typically a polygon, but JTS may return a `Point` or `LineString` for degenerate inputs), [ST_Box2D](Box2D-Constructors/ST_Box2D.md) always returns a typed `Box2D` value. Prefer the typed form when downstream code only needs the four bounds, and prefer the geometry form when downstream code expects a `Geometry`.
## Box2D Constructors
| Function | Return type | Description | Since |
| :--- | :--- | :--- | :--- |
| [ST_Box2D](Box2D-Constructors/ST_Box2D.md) | Box2D | Return the planar bounding box of a Geometry as a Box2D. | v1.9.1 |
| [ST_MakeBox2D](Box2D-Constructors/ST_MakeBox2D.md) | Box2D | Build a Box2D from two corner POINT geometries. | v1.9.1 |
| [ST_GeomFromBox2D](Box2D-Constructors/ST_GeomFromBox2D.md) | Geometry | Convert a Box2D to a closed rectangular polygon Geometry (degenerate boxes return a Point or LineString). | v1.9.1 |
## Box2D Accessors
| Function | Return type | Description | Since |
| :--- | :--- | :--- | :--- |
| [ST_XMin](Box2D-Accessors/ST_XMin.md) | Double | Return the minimum X coordinate of a Box2D. | v1.9.1 |
| [ST_YMin](Box2D-Accessors/ST_YMin.md) | Double | Return the minimum Y coordinate of a Box2D. | v1.9.1 |
| [ST_XMax](Box2D-Accessors/ST_XMax.md) | Double | Return the maximum X coordinate of a Box2D. | v1.9.1 |
| [ST_YMax](Box2D-Accessors/ST_YMax.md) | Double | Return the maximum Y coordinate of a Box2D. | v1.9.1 |
The same `ST_XMin` / `ST_YMin` / `ST_XMax` / `ST_YMax` functions also accept `Geometry` inputs — see [Bounding Box Functions](../Geometry-Functions.md#bounding-box-functions).
## Box2D Predicates
`Box2D` inputs are accepted by the existing `ST_Intersects` / `ST_Contains` / `ST_DWithin` predicates as type-dispatched overloads — there are no separate `ST_Box*` functions.
| Function | Return type | Description | Since |
| :--- | :--- | :--- | :--- |
| [ST_Intersects](../Predicates/ST_Intersects.md) | Boolean | Closed-interval bbox intersection on both axes when both arguments are `Box2D`. Matches PostGIS `&&` on `box2d`. | v1.9.1 |
| [ST_Contains](../Predicates/ST_Contains.md) | Boolean | Closed-interval bbox containment on both axes when both arguments are `Box2D`. Matches PostGIS `~` on `box2d`. | v1.9.1 |
| [ST_DWithin](Box2D-Predicates/ST_DWithin.md) | Boolean | Closed-interval planar distance test between two Box2D rectangles. | v1.9.1 |
## Box2D Functions
| Function | Return type | Description | Since |
| :--- | :--- | :--- | :--- |
| [ST_Expand](Box2D-Functions/ST_Expand.md) | Box2D | Expand a Box2D by a per-axis or uniform delta. | v1.9.1 |
| [ST_AsText](Box2D-Functions/ST_AsText.md) | String | Return the `BOX(xmin ymin, xmax ymax)` text representation of a Box2D. | v1.9.1 |
## Box2D Aggregates
| Function | Return type | Description | Since |
| :--- | :--- | :--- | :--- |
| [ST_Extent](../Aggregate-Functions/ST_Extent.md) | Box2D | Return the planar bounding box of all geometries in a column as a Box2D. Empty and NULL inputs are skipped. Mirrors PostGIS `ST_Extent`. | v1.9.1 |
## Type conversion
Catalyst recognises SQL `CAST` between `Box2D` and `Geometry`:
| Cast | Equivalent function | Notes |
| :--- | :--- | :--- |
| `CAST(geom AS box2d)` | [ST_Box2D(geom)](Box2D-Constructors/ST_Box2D.md) | Planar bounding box of the geometry. |
| `CAST(box AS geometry)` | [ST_GeomFromBox2D(box)](Box2D-Constructors/ST_GeomFromBox2D.md) | Closed rectangular polygon (Point/LineString for degenerate boxes). |
The cast forms require the Sedona SQL parser extension (`spark.sql.extensions=org.apache.sedona.sql.SedonaSqlExtensions`); the function forms work in any Sedona-enabled session.
## Query optimization
Box2D-typed columns are first-class participants in Sedona's spatial optimizer:
- **Filter pushdown.** `ST_Intersects` / `ST_Contains` over a `Box2D` column and a literal `Box2D` push down to Parquet row-group statistics on the column's underlying `xmin` / `ymin` / `xmax` / `ymax` leaves. See [Query optimization → Box2D filter pushdown](../Optimizer.md#box2d-filter-pushdown).
- **Spatial joins.** `ST_Intersects` and `ST_Contains` between two `Box2D` columns route through the same physical operators (`RangeJoinExec`, `BroadcastIndexJoinExec`) used for the Geometry-typed forms — the dataType-aware planner picks the bbox path when both children are `Box2DUDT`. See [Query optimization → Range join](../Optimizer.md#range-join) and [Broadcast index join](../Optimizer.md#broadcast-index-join).