sql - POSTGRES - 将(子)表达式错误评估为 NULL
问题描述
我在 Postgres 表中有传感器数据,其中measurements
包含id
, timestamp
, s0
, s1
, s2
, ...
此外,列上有一个索引(id, timestamp)
。我想允许动态数学表达式(在下面的示例中:)sin(s3)*0.1000/s5
用于计算派生值。
SELECT
timestamp,
trunc((sin(s3) * 0.1000/s5)::numeric, 3) AS "calculated"
FROM measurements
WHERE id = 42
ORDER BY timestamp DESC
LIMIT 10000;
显然,这很容易出现“除以零”错误,这将使查询失败。有没有办法捕捉这个错误并返回例如NULL
错误发生的计算值?
灵感来自
我已经尝试定义一个解析公式并返回异常的postgres
函数。上面 SQL 语句的第三行现在显示为eval_numeric(sensors int[], formula text)
NULL
trunc(eval_numeric(ARRAY[s3,s5],'sin(var1)*0.1/var2'), 3) AS "calculated"
这给出了所需的行为,但报告的执行时间EXPLAIN ANALYZE
增加了 20 倍(~20ms -> ~400ms)。还有其他想法吗?
更新
要评估的动态表达式源于 Web 应用程序用户。所以上面的公式只是一个例子(可能需要检查平方根的负参数)。我宁愿有一个通用的错误检查可能性,也希望在数学表达式中没有逻辑。这对最终用户来说会更容易,我可以验证允许的数学,例如使用数学解析器,从而防止 SQL 注入。
解决方案
你能把表达式改成这样吗?
SELECT timestamp,
trunc((sin(s3) * 0.1000/nullif(s5, 0))::numeric, 3) AS "calculated",
FROM measurements
WHERE id = 42
ORDER BY timestamp DESC
LIMIT 10000;
这是完成您想做的事情的最简单方法。
推荐阅读
- excel - 在 Excel 中的工作表函数之间传递 VBA 类的实例
- reactjs - 我在反应钩子项目中的 POST 请求上有 400 个代码
- regex - 字符串的泛化和状态机优化
- postgresql - 尝试生成 Angular 客户端代码时出现“无法确定合适的驱动程序类”
- git - 文件夹路径旁边的 (master) 是什么意思?
- python - Python - Web Scrape - 使用列表中的条目搜索字符串以进行精确匹配
- flutter - 滚动时多次重建 PageView 和 StreamBuilder
- java - Spring Data Rest 在一个包中添加所有投影
- python - 多次发现后出现美丽的soup.find错误
- android-source - 如何使用ccache来加速aosp的编译?