我有一个从 SQL 执行时表现出色的查询。
它是表和查询之间的连接。这两个表都有接近 400 万条记录。 我试图提供提示的文档表上有位图索引。当我从蟾蜍那里看到时,解释计划确实表明它们正在帮助加入。
我提供了 2 个其他提示,看看它们是否有帮助。一种用于直接路径 APPEND,另一种用于利用 pda 上现有的 BTree 索引。
当此查询针对 SQL 中的替换变量运行时,结果是即时的,但过程中的相同查询需要 8 秒或更长时间。
除了 DBA 尚未提交的程序计划外,您认为我可能有什么明显的遗漏?提前致谢。
INSERT /*+ APPEND */
INTO tmp_search_gross_docs (document_id,
last_name,
first_name,
person_doc_association_id,
association_date)
SELECT /*+INDEX(pda IDX_DOC_PDOC_DOCID ) USE_NL(pda doc) */
pda.document_id,
last_name,
first_name,
person_doc_association_id,
association_date
FROM pda,
(SELECT /*+INDEX_COMBINE(attr IDX_BMP_SEARCH_FN,IDX_BMP_SEARCH_LN)*/
document_id, last_name, first_name
FROM doc attr
WHERE first_name LIKE l_first_name OR last_name LIKE l_last_name) doc
WHERE pda.document_id = doc.document_id;
) doc
WHERE pda.document_id = doc.document_id;
解释计划(来自 Toad 的绑定(bind)变量)
INSERT STATEMENT ALL_ROWSCost:1,086,010 字节:15,309,420 基数:364,510
11 加载为选择 TMP_SEARCH_GROSS_DOCS
10 TABLE ACCESS BY INDEX ROWID TABLE PDA 成本:3 字节:20 基数:1
9 个嵌套循环成本:1,086,010 字节:15,309,420 基数:364,510
7 通过索引 ROWID 表 ATTR 访问表 成本:23,893 字节:8,019,220 基数:364,510
6 位图转换为行
5 位图或
2 位图合并
1 位图索引范围扫描索引(位图)IDX_BMP_SEARCH_FN
4 位图合并
3 位图索引范围扫描索引(位图)IDX_BMP_SEARCH_LN
8 INDEX RANGE SCAN INDEX IDX_PDA_EXP_DOC 成本:2 基数:1
基数 364,510 似乎不对,因为该表包含 3738562 行,而对于 WHERE 中列的替换值,计数仅为 8892。
但同样,这个计划至少告诉我正在使用正确的索引,并且在 toad 编辑器中运行得非常快。
来自 PL/SQL 的实际计划仍然不可用。
不确定这是否会增加一些有值(value)的信息。但是思想还是会编辑的。谢谢
最佳答案
首先,我不认为使用 append 插入 GTT 有任何逻辑。我可能是错的,但据我所知,附加绕过缓冲区缓存并直接写入文件,它写入高水位线以上并且在提交之前不允许查询。 GTT 不在常规数据文件上 - 它在临时文件上,并且在提交时被截断(默认设置)。
我认为,如果您不需要在查询后操作数据,请考虑向应用程序返回一个引用游标。它基本上是同一件事 - 许多 DAL 层都是以这种方式实现的。
如果您仍然想要 GTT,我会检查我的临时文件分配,包括大小和实际磁盘 - 您的 DBA 可能已将它们放在不同的设备上。
关于sql - 从 PL/SQL 插入到临时表 GTT 非常慢,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/15978395/