MySQL ST_MakeEnvelope 怎样从两个点构造矩形范围
在做“按两个坐标点筛选一块范围”的查询时,我更愿意先把范围本身表达成一个几何对象,而不是手写四个角点。MySQL 的 ST_MakeEnvelope() 就是为这个任务准备的:给它两个 Point,它会在笛卡尔坐标平面上返回两点的包络范围。
官方地址:https://dev.mysql.com/doc/refman/8.4/en/spatial-convenience-functions.html
先记住一个容易忽略的细节:返回值不一定永远是 Polygon。两点重合时返回 Point;只在水平或垂直方向对齐时返回 LineString;只有一般的对角点关系才返回 Polygon。下面按这个边界把 SQL 跑通。
先把两个坐标点准备好
函数签名只有两个参数:ST_MakeEnvelope(pt1, pt2)。参数必须是 Point,点的顺序不影响最终包络范围,但坐标的含义要在业务侧先约定清楚。示例用平面坐标,不把经纬度直接当成地球曲面距离。
-- 用 WKT 创建两个 Point;这里的 x、y 是抽象笛卡尔坐标
SET @pt1 = ST_GeomFromText('POINT(10 20)');
SET @pt2 = ST_GeomFromText('POINT(30 50)');
-- 先确认输入确实是点,避免把 LineString 等其他几何类型传进去
SELECT ST_GeometryType(@pt1) AS pt1_type,
ST_GeometryType(@pt2) AS pt2_type;
如果你的表字段已经是空间类型,可以直接把字段或变量传入,不必先转换成 WKT。WKT 更适合在示例、脚本参数和排查时明确表达输入。
用 ST_MakeEnvelope 生成矩形范围
把两个 Point 传入函数,再用 ST_AsText() 转成容易阅读的 WKT。对于 (10,20) 和 (30,50) 这样的普通对角点,返回的闭合 Polygon 会依次经过左下、右下、右上、左上,再回到起点。
-- 两个点是矩形的对角点,函数会补出另外两个角 SELECT ST_AsText(ST_MakeEnvelope(@pt1, @pt2)) AS envelope_wkt; -- 同时读取几何类型,避免把所有结果都假设成 Polygon SELECT ST_GeometryType(ST_MakeEnvelope(@pt1, @pt2)) AS envelope_type;
普通情况下会得到类似 POLYGON((10 20,30 20,30 50,10 50,10 20)) 的结果。这里的闭合首尾相同,是多边形环的正常表达。

三种点位关系对应三种返回形态
这一步是实际使用中最容易踩坑的地方:函数描述的是“包络”,不是“强制生成一个面积大于零的矩形”。当两个点的几何关系退化时,结果也会退化。
| 两个点的关系 | 返回类型 | 适合怎样处理 |
|---|---|---|
| 坐标完全相同 | Point | 表示一个位置,不能按面来计算面积 |
| 仅 x 相同或仅 y 相同 | LineString | 表示水平或垂直线段,先判断类型再做空间运算 |
| x、y 都不同 | Polygon | 表示普通矩形包络,可继续用于面关系判断 |
-- 用三个案例观察退化结果;每个案例都读取文本和类型
SELECT 'same-point' AS case_name,
ST_AsText(ST_MakeEnvelope(
ST_GeomFromText('POINT(10 20)'),
ST_GeomFromText('POINT(10 20)')
)) AS result_wkt,
ST_GeometryType(ST_MakeEnvelope(
ST_GeomFromText('POINT(10 20)'),
ST_GeomFromText('POINT(10 20)')
)) AS result_type
UNION ALL
SELECT 'vertical-line',
ST_AsText(ST_MakeEnvelope(
ST_GeomFromText('POINT(10 20)'),
ST_GeomFromText('POINT(10 50)')
)),
ST_GeometryType(ST_MakeEnvelope(
ST_GeomFromText('POINT(10 20)'),
ST_GeomFromText('POINT(10 50)')
));
如果后续 SQL 必须使用 Polygon 的面积、外环或面关系,建议在应用层先判断 ST_GeometryType(),或者在输入校验阶段要求两个点的 x 与 y 都不同。不要等到后续空间函数报错才猜测原因。

生产查询前检查 SRID 与坐标边界
这个函数的计算是在笛卡尔坐标系中完成的,结果几何的 SRID 为 0。因此,如果业务字段使用的是有明确空间参考的几何对象,不要把“构造包络”误认为“已经完成经纬度地理计算”。地图范围、距离和投影转换属于另外的空间问题,应在明确坐标系后单独设计。
官方规则还给出几项硬边界:
- 两个参数必须都是 Point,否则会产生参数错误。
- 任一点坐标为无穷大或 NaN 时,会产生 GIS 无效数据错误。
- 地理空间参考系统不支持这个函数的调用。
- 涉及多个几何参数的空间函数通常要求参数处于同一 SRS;不要混用不同空间参考。
-- 发布前记录结果类型和 SRID,便于排查坐标系误解
SELECT ST_GeometryType(envelope) AS geometry_type,
ST_SRID(envelope) AS result_srid,
ST_AsText(envelope) AS result_wkt
FROM (
SELECT ST_MakeEnvelope(
ST_GeomFromText('POINT(10 20)'),
ST_GeomFromText('POINT(30 50)')
) AS envelope
) AS prepared_range;
这段查询的重点不是多包一层子查询,而是把“结果类型、SRID、可读文本”一起记录下来。排查坐标范围为空、面积为零或和地图预期不一致时,这三个字段通常比只看一段 WKT 更快定位问题。
和业务表做范围筛选时怎么落地
如果表里保存的是 Point,可以把包络作为一个明确的查询参数,再结合实际空间关系函数使用。这里不把示例包装成某个固定业务表结构,避免让字段名掩盖核心逻辑;关键是先确认两端使用同一套坐标约定,并在 SQL 中保留参数来源。
-- 先构造范围参数;实际项目中可替换为绑定参数
SET @range = ST_MakeEnvelope(
ST_GeomFromText('POINT(10 20)'),
ST_GeomFromText('POINT(30 50)')
);
-- 假设 locations.position 是 Point;先用类型与范围条件表达业务意图
SELECT id, name
FROM locations
WHERE ST_Within(position, @range); -- 只返回位于包络范围内的点
真正上线时还要结合表结构、索引和数据规模选择执行方式。ST_MakeEnvelope() 负责构造几何范围,不会自动替你完成空间索引设计,也不会替你判断输入坐标到底是平面坐标还是经纬度。
常见问题
ST_MakeEnvelope 可以直接传经纬度吗?
它按笛卡尔坐标平面计算,不能把调用结果直接当成球面或椭球面上的地理范围。若数据使用地理 SRS,先按业务坐标系重新设计空间运算。
为什么两个点传进去却不是 Polygon?
两点重合会退化为 Point,水平或垂直对齐会退化为 LineString。只有 x 和 y 都不同的普通对角点关系才返回 Polygon。
能否用一个 Point 和一个字符串参数?
不能。两个参数都需要是 Point;字符串应先通过合适的几何构造函数转换,并在转换后确认类型和坐标边界。
怎样确认生成的范围是预期的?
同时读取 ST_AsText()、ST_GeometryType() 和 ST_SRID(),再核对两个输入点的坐标顺序。不要只根据一张地图截图判断函数是否正确。
总结
MySQL ST_MakeEnvelope(pt1, pt2) 的用法可以压缩成三句话:两个参数必须是 Point;普通对角点生成 Polygon;重合或水平/垂直对齐会产生退化的 Point 或 LineString。把返回类型和 SRID 一并记录,范围查询就不会因为“看起来像矩形”而掩盖坐标系和几何类型问题。
Go x/image/riff 容器声明长度大于实际输入怎么办
- 上一篇
- Go x/image/riff 容器声明长度大于实际输入怎么办
- 下一篇
- Go debug/dwarf SeekPC 为什么找不到某些地址
-
- 数据库 · MySQL | 31分钟前 |
- MySQL ST_AsGeoJSON 怎样控制几何输出的小数位
- 430浏览 收藏
-
- 数据库 · MySQL | 32分钟前 |
- MySQL ST_IsClosed 怎样判断折线是否闭合
- 289浏览 收藏
-
- 数据库 · MySQL | 33分钟前 |
- MySQL ST_GeometryN 怎样读取集合中的指定几何对象
- 264浏览 收藏
-
- 数据库 · MySQL | 36分钟前 |
- MySQL ST_NumInteriorRing 怎样统计多边形内部孔洞
- 279浏览 收藏
-
- 数据库 · MySQL | 38分钟前 |
- MySQL ST_ExteriorRing 怎样提取多边形外环
- 330浏览 收藏
-
- 数据库 · MySQL | 39分钟前 |
- MySQL ST_Longitude 怎样读取地理点的经度
- 198浏览 收藏
-
- 数据库 · MySQL | 40分钟前 |
- MySQL ST_SwapXY 怎样交换几何对象的坐标分量
- 381浏览 收藏
-
- 数据库 · MySQL | 43分钟前 |
- MySQL ST_HausdorffDistance 怎样衡量两个几何集合的最大偏离
- 296浏览 收藏
-
- 数据库 · MySQL | 46分钟前 | MySQL · mysql ST_FrechetDistance 空间函数 轨迹比较 LineString
- MySQL ST_FrechetDistance 怎样比较两条轨迹的形状差异
- 488浏览 收藏
-
- 数据库 · MySQL | 48分钟前 |
- MySQL ST_LineInterpolatePoint 怎样定位折线上的比例位置
- 399浏览 收藏
-
- 数据库 · MySQL | 49分钟前 | MySQL · 数据校验 · 空间数据 MySQL ST_Validate 几何有效性 WKT ST_IsValid
- MySQL ST_Validate 怎样检查并返回有效几何对象
- 387浏览 收藏
-
- 数据库 · MySQL | 50分钟前 |
- MySQL ST_Simplify 怎样减少折线中的冗余点
- 384浏览 收藏
-
- 前端进阶之JavaScript设计模式
- 设计模式是开发人员在软件开发过程中面临一般问题时的解决方案,代表了最佳的实践。本课程的主打内容包括JS常见设计模式以及具体应用场景,打造一站式知识长龙服务,适合有JS基础的同学学习。
- 543次学习
-
- GO语言核心编程课程
- 本课程采用真实案例,全面具体可落地,从理论到实践,一步一步将GO核心编程技术、编程思想、底层实现融会贯通,使学习者贴近时代脉搏,做IT互联网时代的弄潮儿。
- 516次学习
-
- 简单聊聊mysql8与网络通信
- 如有问题加微信:Le-studyg;在课程中,我们将首先介绍MySQL8的新特性,包括性能优化、安全增强、新数据类型等,帮助学生快速熟悉MySQL8的最新功能。接着,我们将深入解析MySQL的网络通信机制,包括协议、连接管理、数据传输等,让
- 500次学习
-
- JavaScript正则表达式基础与实战
- 在任何一门编程语言中,正则表达式,都是一项重要的知识,它提供了高效的字符串匹配与捕获机制,可以极大的简化程序设计。
- 487次学习
-
- 从零制作响应式网站—Grid布局
- 本系列教程将展示从零制作一个假想的网络科技公司官网,分为导航,轮播,关于我们,成功案例,服务流程,团队介绍,数据部分,公司动态,底部信息等内容区块。网站整体采用CSSGrid布局,支持响应式,有流畅过渡和展现动画。
- 485次学习
-
- PubMedQA
- 深入了解PubMedQA生物医学问答数据集,涵盖其核心功能、使用方法及在临床决策、药物研发等场景的应用,助力提升NLP模型性能。
- 726次使用
-
- H2O EvalGPT
- H2O EvalGPT是H2O.ai推出的开源LLM评估平台,提供详细的大模型性能排行榜、行业特定基准测试及A/B测试功能,助您快速选择最适合项目的高性能大语言模型。
- 733次使用
-
- LMArena
- LMArena是加州大学伯克利分校推出的AI模型匿名评测平台。通过盲测投票机制,用户可对比不同大模型回答并生成实时排行榜,助力开发者优化模型及用户选择最佳AI工具。
- 809次使用
-
- HELM
- 深入了解斯坦福推出的HELM(Holistic Evaluation of Language Models)大模型评测体系。本文解析其核心功能、安装配置步骤及应用场景,涵盖准确性、公平性、鲁棒性等多维度指标,助力开发者全面优化语言模型性能。
- 770次使用
-
- MMBench
- MMBench是由上海人工智能实验室等机构联合推出的多模态基准测试平台,提供细粒度能力评估、大规模数据集及VLMEvalKit工具。本文详细介绍其核心功能、安装使用方法及应用场景,助力开发者全面评估多模态模型性能。
- 609次使用
-
- MySQL JSON_TABLE 展开数组时如何保留缺失字段
- 2026-09-10 501浏览
-
- MySQL 分区表怎么处理跨分区唯一键:分区列约束与建表取舍
- 2026-08-30 501浏览
-
- MySQL权限管理设置全攻略
- 2026-03-29 501浏览
-
- MySQL分片实现方法及常见方案解析
- 2025-06-24 501浏览
-
- MySQL表空间碎片怎么清理?超详细优化教程
- 2025-06-13 501浏览

