2012-02-28 98 views
-1

对不起,只是清除我的问题。扩展这一问题Optimizing sqlite query为什么第一个查询比第二个查询快?

我有一个表:

CREATE TABLE IF NOT EXISTS [app_status](
[id] INTEGER PRIMARY KEY AUTOINCREMENT NOT NULL , 
[status] TEXT DEFAULT NULL, 
[type] INTEGER 
) 

我有两个指标。一个在status上,另一个在type上。哪个查询运行得更快,为什么?

SELECT COALESCE(min(type), 0) 
    FROM app_status 
WHERE status IS NOT NULL 
    AND type IN (1,2) limit 1 

查询计划O/P

0|0|0|SEARCH TABLE app_status USING INDEX idx_type (mailbox_type=?) (~10 rows) 
0|0|0|EXECUTE LIST SUBQUERY 1 

或者......

SELECT type FROM 
app_status WHERE 
status IS NOT NULL 
ORDER BY type limit 1 

查询计划O/P

0|0|0|SCAN TABLE app_status USING INDEX idx_type (~500000 rows) 
+3

你生成执行计划? – Randy 2012-02-28 17:29:43

+0

@Randy我添加了查询计划o/p,但无法理解哪里有太大差异bw /有两个查询计划o/p – 2012-02-28 17:43:53

+1

查询可能不会返回相同的结果,这可能会解释计划中的差异 – Sparky 2012-02-28 17:49:50

回答

2

第一个查询返回零或一行匹配WHERE子句中的条件(where status is not null and type in (1,2),in未指定的顺序。

第二个查询查找符合WHERE子句中条件的所有行(where status is not null),按类型对它们进行排序,然后返回零或1行。

你应该注意两个查询,虽然他们可能返回相同的结果,不保证。特别是,第二个查询返回的行将按照type的顺序返回结果集的第一行,而不管type是什么值。如果type的最低值是“状态不为空”,比如157,那么这就是你将要获得的行。在这种情况下,第一个查询将返回0行。

但假设typestatus被索引,并且查询可以使用一个或多个索引,那么我的怀疑是第一个查询会更快,因为它可以直接查找所需的行。

不过这很大程度上取决于数据的形状(有多少数据呢?它是如何分配的?等等),指数是否是“覆盖”(如果索引没有覆盖中的所有列查询的话,就必须做额外的I/O,以获得覆盖所有列所需的数据页(S)。

编辑注意看着你张贴的执行计划(不知道Sqllite),第一计划说它应该返回约10行;第二约50,000行,你认为哪一个可能会更快?

+0

我将在该表中只有2000行。 和问题标记我有类型和状态的索引。 – 2012-02-28 18:04:33

2

你应该:

CREATE INDEX idx_app_staus ON app_status (status, type) 

这样的数据库angine将不必查找所有的行,它可以找到它所需要的where子句中的确切行。我不知道是哪个查询速度更快becouse他们不返回相同的结果集,但以上所有这些类型的查询的指数将是快速的。其他两个指数可能会被丢弃。

+0

执行计划中有完整的tablle扫描。我认为你是对的,通过假设没有索引的where子句是问题。 – 2012-02-28 18:35:03

相关问题