使用未排序的时间范围减少表中的查询时间

时间:2012-06-22 10:38:25

标签: c++ sql sqlite

前几天我对此事有疑问,但我仍然想知道如何调整我在此查询中的表现。

我有一个看起来像这样的表(SQLite)

CREATE TABLE ZONEDATA (
TIME INTEGER  NOT NULL,
CITY INTEGER  NOT NULL,
ZONE INTEGER  NOT NULL,
TEMPERATURE DOUBLE,
SERIAL INTEGER ,
FOREIGN KEY (SERIAL) REFERENCES ZONES,
PRIMARY KEY ( TIME, CITY, ZONE));

我正在运行这样的查询:

SELECT temperature, time, city, zone from zonedata
WHERE (city = 1) and (zone = 1) and (time BETWEEN x AND y);

x和y是变量,它们之间可能有几十万个变量。

温度范围从-10.0到10.0,城市和区域从0到20(在这种情况下,它是1和2,但可以是其他东西)。从不同的区域和城市以约5-6秒的间隔连续记录记录。这会创建大量数据,并不一定意味着每个记录都以正确的时间顺序记录。

问题是如何在很大的时间范围内优化记录检索(记录未按时间正确排序100%)。这可能需要很长时间,特别是当我从几个城市和区域检索时。这意味着多次使用不同的参数运行上述查询。我正在寻找的是对查询,表结构(最好不是)或其他可更改设置的具体更改。

我使用它的应用程序是用c ++实现的。

3 个答案:

答案 0 :(得分:1)

您的数据已按Time排序。

通过在(Time, City, Zone)上设置主键,具有相同Time值的所有记录将彼此相邻。 (除非您在其他地方指定了CLUSTER INDEX,但我对SQLite不太熟悉,知道这是否可行。)

但是,在您的特定情况下,这意味着您想要的记录不会彼此相邻。相反,他们是成群结队的。每组记录都有(city=1, zone=1)并具有相同的时间值。一组用于Time1,另一组用于Time2等等。

就像把它全部放在Excel中并按时间排序,然后按城市,然后按区域排序。

将所需的所有记录(针对同一城市和区域)更改为(City, Zone, Time)


但请注意,如果您对all cities and zones but a time = ???的查询也提出了我建议的密钥并不完美,那么您的原始密钥会更好。

出于这个原因,您可能希望/需要为不同的查询添加不同顺序的不同索引。


这意味着为了给您一个特定的推荐解决方案,我们需要知道您将要运行的特定查询。我建议的键/索引顺序对于您的简化示例可能是理想的,但现实情况可能不同,足以保证不同的索引。

答案 1 :(得分:0)

您可以索引这些列,它会在内部对其进行排序以便更快地进行查询,但您将看不到它。

答案 2 :(得分:0)

对于数据库between很难优化。解决此问题的一种方法是添加额外字段,以便将between替换为=。例如,如果您添加day字段,则可以查询:

where  city = 1 and zone = 1 and day = '2012-06-22' and 
       time between '2012-06-22 08:00' and '2012-06-22 12:00'

此查询相对较快,索引位于city, zone, day

这需要考虑选择适当的额外字段。它需要额外的代码来维护该字段。如果此查询位于应用程序的重要性能路径中,则可能值得。