子查询中用ST_DWithin或STDistance易报错或极慢,主因是类型丢失、索引失效、语义错位;须显式表别名、统一geometry/geography类型、用EXISTS替代IN、注意SQL Server经纬序及SRID、BigQuery需满足最小搜索区域。

直接用子查询套 ST_DWithin 或 STDistance 大概率报错或慢得离谱——不是语法错,是类型丢失、索引失效、语义错位三重坑同时踩中。
PostgreSQL里子查询调用ST_DWithin报function does not exist?
错误信息看着像函数没装,其实是参数类型推导失败。子查询里写的 ST_DWithin(geom, $1, 5000),geom 在子查询上下文中没绑定表别名,解析器认不出它是 geometry(POINT,4326),只当 unknown,自然匹配不到函数签名。
- 必须显式写出表别名:子查询
FROM cities b,然后用b.geom,不能只写geom - 两个几何参数必须同类型:都用
geometry(单位是坐标系单位,4326下是度),或都转成geography(单位是米)——混用必崩 - 如果原始列是
geometry(POINT,4326)又想按米算,写成ST_DWithin(c.geom::geography, b.geom::geography, 5000),别漏掉双冒号强制转换 -
EXISTS比IN更稳:它不依赖子查询返回值,只判断存在性,优化器能下推空间谓词,避免先全表扫描再过滤
SQL Server存储过程中用GEOGRAPHY::Point()总算错位置?
90% 是经纬度顺序写反了。GEOGRAPHY::Point(lat, lon, 4326),纬度在前、经度在后——前端传的常是 lng/lat,直接塞进去就偏到南大西洋。
- 查表字段名:如果是
longitude和latitude,调用时必须交换:GEOGRAPHY::Point(t.latitude, t.longitude, 4326) - SRID 必须显式写
4326,缺了会静默失败或返回 0 - 别在
WHERE里反复构造:GEOGRAPHY::Point(a.lat,a.lng,4326).STDistance(@p)每行都新建对象,性能炸;改用 CTE 预转:SELECT ..., GEOGRAPHY::Point(lat,lng,4326) AS geo FROM ... - 空间索引只能建在
GEOGRAPHY类型列上,建在float列上等于没建
BigQuery里用PLACES_COUNT_V2批量查地点数却返回空?
不是 API 挂了,是触发了最小搜索区域限制:函数强制要求输入地理范围 ≥ 40m × 40m(1600 平方米)。传一个点坐标或极小 bounding box,直接被截断,返回 0 行。
- 输入必须是
TABLE参数,不能是单个POINT常量;用UNNEST构造多行地理范围更安全 - 如果只查单点附近数量,得先用
ST_BUFFER扩一圈,比如ST_Buffer(ST_GeogPoint(lng,lat), 50)生成 50 米半径圆面再喂给函数 -
PLACES_COUNT_V2返回带place_id的结果,但仅限示例 ID(最多 250 个),真要拉详情得拿这些 ID 再查 Places API - 它不支持复杂联接或聚合计算,要算平均评分、做 JOIN,得切回直接查
places数据集
真正卡住人的从来不是函数怎么写,而是类型隐式转换、索引是否命中、输入范围是否合规这三点——它们不出现在错误信息里,但每一条都能让查询从毫秒变分钟。

















