我试图理解为什么第一个查询会比第二个查询快:
SELECT * FROM DBADMIN.CR_TICKET WHERE QUEUE_ID=005555 AND STATUS=4
和
SELECT TICKET_ID FROM DBADMIN.CR_TICKET WHERE QUEUE_ID=005555 AND STATUS=4
第一个运行大约需要一分钟并返回所有字段。第二个我只是在几分钟后停下来,因为它花了太长时间。TICKET_ID 是有效的列名。我是数据库和 sql 的新手,并且使用 vb.net 并参考了 oracle 即时客户端 11。
Using connection As New OracleConnection()
Dim command As OracleCommand = connection.CreateCommand()
Dim reader As OracleDataReader = command.ExecuteReader()
Dim str As String
Dim strFieldName As String
Dim strFieldType As String
Dim sql As String = "SELECT * FROM DBADMIN.CR_TICKET WHERE QUEUE_ID=005555 AND STATUS=4"
connection.ConnectionString = connectionString
connection.Open()
command.CommandText = sql
While reader.Read()
str = ""
strFieldName = ""
strFieldType = ""
For e = 0 To reader.FieldCount - 1
strFieldName = reader.GetName(e)
strFieldType = reader.GetDataTypeName(e)
str = str & strFieldName & " " & strFieldType & ": " & reader(e).ToString & vbCrLf
Next
Console.Write(str & vbCrLf & vbCrLf)
End while
2013 年 3 月 4 日更新:
首先感谢您的出色建议,我最终能够让 sql plus 运行并返回以下执行计划。我昨天做了很多阅读,发现我的查询速度很慢的原因之一是我正在搜索的列没有被索引。我发现主键列(存在于每个表中)默认情况下是索引的。我将我的 sql 字符串更改为:
SQL> SELECT * FROM DBADMIN.CR_TICKET WHERE TICKET_ID > 'CR00000000' AND STATUS=4 AND (QUEUE_ID=005555 OR QUEUE_ID=005556) ORDER BY PRIORITY, TROUBLE_START;
| Id | Operation | Name | Rows | Bytes | Cost (%CPU)
| Time |
--------------------------------------------------------------------------------
------------
| 0 | SELECT STATEMENT | | 1 | 401 | 6 (17)
| 00:00:01 |
| 1 | SORT ORDER BY | | 1 | 401 | 6 (17)
| 00:00:01 |
|* 2 | TABLE ACCESS BY INDEX ROWID| CR_TICKET | 1 | 401 | 5 (0)
| 00:00:01 |
|* 3 | INDEX RANGE SCAN | CRT_TID_IDX | 1 | | 4 (0)
| 00:00:01 |
--------------------------------------------------------------------------------
这运行得相当快。我了解到我的原始查询正在读取数据库中的每条记录以匹配我的陈述。通过稍微不同地构造查询以包含索引列,它基本上只搜索主数据库的一部分。
SQL> SELECT * FROM DBADMIN.CR_TICKET WHERE QUEUE_ID=005555 AND STATUS=4 AND PRIORITY=1;
| Id | Operation | Name | Rows | Bytes | Cost (%CPU)
| Time |
--------------------------------------------------------------------------------
------------
| 0 | SELECT STATEMENT | | 1 | 401 | 14864 (1)
| 00:02:59 |
|* 1 | TABLE ACCESS BY INDEX ROWID| CR_TICKET | 1 | 401 | 14864 (1)
| 00:02:59 |
|* 2 | INDEX RANGE SCAN | CRT_STAT_IDX | 230K| | 408 (2)
| 00:00:05 |
SQL> SELECT DBADMIN.CR_TICKET.TICKET_ID FROM DBADMIN.CR_TICKET WHERE QUEUE_ID=005555 AND STATUS=4 AND PRIORITY=1;
| Id | Operation | Name | Rows | Bytes | Cost (%CPU)
| Time |
--------------------------------------------------------------------------------
------------
| 0 | SELECT STATEMENT | | 1 | 24 | 14845 (1)
| 00:02:59 |
|* 1 | TABLE ACCESS BY INDEX ROWID| CR_TICKET | 1 | 24 | 14845 (1)
| 00:02:59 |
|* 2 | INDEX RANGE SCAN | CRT_STAT_IDX | 230K| | 408 (2)
| 00:00:05 |
--------------------------------------------------------------------------------
2013 年 5 月 25 日更新
感谢您提供帮助,我很感激。我终于有机会重新审视这个项目并尝试了您建议的查询。第一个运行良好,第二个没有返回任何结果。您提到了索引功能。这会在数据库上创建一个永久索引吗?我不想那样做。
select status, priority, count(*)
from dbadmin.cr_ticket
group by status, priority;