sql - Firebird 中的慢查询执行

标签 sql performance firebird

我执行的 SQL 查询如下:

update elements E
    set E.END_I = (select n.node_num
                   from nodes N 
                   where abs(E.X_I - N.XI) < 0.001 and
                         abs(E.Y_I - N.YI) < 0.001 and
                         abs(E.Z_I - N.ZI) < 0.001
                  )

完成大约需要 24 秒,我阅读了有关 firebird 故障排除的信息 Why is my database query slow?它指示为表中的相关字段创建索引,并且我在节点和元素表中为 XI、YI、ZI 字段添加了递减/递增索引。但是性能仍然很慢,数据库中有 6677 行,我使用 FlameRobin 作为 SQL 编辑器。

有趣的是:如 Firebird 故障排除指南中所述

If you see a NATURAL plan going against a big table, you've found the problem



此错误被描述为坏情况和速度减慢的根源,推荐的解决方案是为相关字段创建递减索引。但在我的情况下,即使在定义了指数之后,似乎我仍然受到 Flamerobin 输出中报告的 PLAN (N NATURAL)、PLAN (E NATURAL) 的困扰,如下所示。

我该如何消除它?
Preparing query: update elements E set E.END_I = (select n.node_num from nodes N 
where abs(E.X_I-N.XI)<0.001 and abs(E.Y_I - N.YI)<0.001 and abs(E.Z_I-N.ZI)<0.001 )
Prepare time: 0.004s
PLAN (N NATURAL)
PLAN (E NATURAL)

Executing...
Done.
108818273 fetches, 79227 marks, 4050 reads, 9380 writes.
0 inserts, 6677 updates, 0 deletes, 0 index, 14549183 seq.
Delta memory: 212 bytes.
ELEMENTS: 6677 updates. 
6677 rows affected directly.
Total execution time: 24.038s
Script execution finished.

CREATE DESCENDING INDEX IDX_ELEMENTS1 ON ELEMENTS (Z_I);
CREATE DESCENDING INDEX IDX_XI ON ELEMENTS (X_I);
CREATE DESCENDING INDEX IDX_YI ON ELEMENTS (Y_I);
GRANT DELETE, INSERT, REFERENCES, SELECT, UPDATE
 ON ELEMENTS TO  SYSDBA WITH GRANT OPTION;

CREATE DESCENDING INDEX IDX_NODES1_XI ON NODES (XI);
CREATE DESCENDING INDEX IDX_NODES1_YI ON NODES (YI);
CREATE DESCENDING INDEX IDX_NODES1_ZI ON NODES (ZI);
GRANT DELETE, INSERT, REFERENCES, SELECT, UPDATE
 ON NODES TO  SYSDBA WITH GRANT OPTION;

最佳答案

您的查询因 abs() 而变慢作为裸列索引的函数不适用于表达式。
尝试更改查询以至少让数据库有机会使用索引

update elements E
    set E.END_I = (select n.node_num
                   from nodes N 
                   where N.XI < E.X_I + 0.001 AND N.XI > E.X_I - 0.001
                   AND N.YI < E.Y_I + 0.001 AND N.YI > E.Y_I - 0.001
                   AND N.ZI < E.Z_I + 0.001 AND N.ZI > E.Z_I - 0.001
                  )

关于sql - Firebird 中的慢查询执行,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/34655946/

相关文章:

java - Hibernate 的外键问题(Bug?)

database - 考虑拼写错误和部分结果的数据搜索基础

SQL 对具有类别总计的不同行的非不同权重求和

MySQL引用子查询的结果

c - 算术运算的处理时间不成比例 [C]

performance - Postgresql 数组 && 运算符执行速度低于预期

c++ - 为什么 OpenMP 'simd' 比 'parallel for simd' 有更好的性能?

sql - 如何更正BAT文件中的Select Spool

mysql - 反规范化以减少 COUNT 和 AVG 等聚合函数(计算)的使用 : worth it?

sql - 如何查找 Firebird 数据库中的所有文本 blob 字段