我正在分析Oracle执行计划,并发现了一个令人惊讶的事实.看看这个查询.提示只是为了显示我有一个索引,我希望Oracle将它用于范围扫描:
// execute_at is of type DATE.
PreparedStatement stmt = connection.prepareStatement(
"SELECT /*+ index(my_table my_index) */ * " +
"FROM my_table " +
"WHERE execute_at > ? AND execute_at < ?");
Run Code Online (Sandbox Code Playgroud)
这两个绑定导致完全不同的行为(排除绑定变量偷看问题,我实际上强制执行两个硬解析):
// 1. with timestamps
stmt.setTimestamp(1, start);
stmt.setTimestamp(2, end);
// 2. with dates
stmt.setDate(1, start);
stmt.setDate(2, end);
Run Code Online (Sandbox Code Playgroud)
1)有了时间戳,我得到INDEX FULL SCAN一个过滤谓词
--------------------------------------------------------------
| Id | Operation | Name |
--------------------------------------------------------------
| 0 | SELECT STATEMENT | |
|* 1 | FILTER | |
| 2 | TABLE ACCESS …Run Code Online (Sandbox Code Playgroud)