2013-07-25 4 views
0

Android (SQlite)에서 GTFS 데이터로 작업하고 있습니다. GTFS 데이터로 채워진 데이터베이스에서 쿼리를 선택하면 성능이 향상됩니다. GTFS 데이터의 정지 시간에 대한 SQlite 쿼리

쿼리

는 아래 정류장에서 경로에 관련된 정지 시간을 선택합니다 :

제 1 서브 쿼리는 목요일에 매일 정지 시간을 가져옵니다. 두 번째는 오늘 (2013-07-25) 동안 유효하지 않은 모든 예외 중지 시간을 가져옵니다. 세 번째 것은 오늘 (2013-07-25)에만 유효한 모든 예외 중지 시간을 가져옵니다. 그런 다음 유효하지 않은 항목을 제거하고 유효한 하위 항목을 첫 번째 하위 쿼리에 추가합니다.

select distinct stop_times_arrival_time 
from stop_times, trips, calendar 
where stop_times_trip_id=trip_id 
and calendar_service_id=trip_service_id 
and trip_route_id='11821949021891616' 
and stop_times_stop_id='3377699721872252' 
and calendar_start_date<='20130725' 
and calendar_end_date>='20130725' 
and calendar_thursday=1 
and stop_times_arrival_time>='07:40' 

except 

select stop_times_arrival_time 
from stop_times, trips, calendar, calendar_dates 
where stop_times_trip_id=trip_id 
and calendar_service_id=trip_service_id 
and calendar_dates_service_id = trip_service_id 
and trip_route_id='11821949021891694' 
and stop_times_stop_id='3377699720880977' 
and calendar_thursday=1 
and calendar_dates_exception_type=2 
and stop_times_arrival_time > '07:40' 
and calendar_dates_date = 20130725 

union 

select stop_times_arrival_time 
from stop_times, trips, calendar, calendar_dates 
where stop_times_trip_id=trip_id 
and calendar_service_id=trip_service_id 
and calendar_dates_service_id = trip_service_id 
and trip_route_id='11821949021891694' 
and stop_times_stop_id='3377699720880977' 
and calendar_thursday=1 
and calendar_dates_exception_type=1 
and stop_times_arrival_time > '07:40' 
and calendar_dates_date = 20130725; 

(매우 길다) 계산에는 약 15 초가 걸렸습니다. 시간이 걸리는 3 가지 쿼리 (거의 동일한 방식으로)를 수행하므로이 쿼리를 수행하는 것이 더 좋습니다.

어떻게 개선 할 수 있습니까? 편집

: 여기 스키마입니다 :

table|calendar|calendar|2|CREATE TABLE calendar (
    calendar_service_id TEXT PRIMARY KEY, 
    calendar_monday INTEGER, 
    calendar_tuesday INTEGER, 
    calendar_wednesday INTEGER, 
    calendar_thursday INTEGER, 
    calendar_friday INTEGER, 
    calendar_saturday INTEGER, 
    calendar_sunday INTEGER, 
    calendar_start_date TEXT, 
    calendar_end_date TEXT 
) 
index|sqlite_autoindex_calendar_1|calendar|3| 
table|calendar_dates|calendar_dates|4|CREATE TABLE calendar_dates (
     calendar_dates_service_id TEXT, 
     calendar_dates_date TEXT, 
     calendar_dates_exception_type INTEGER 
) 
table|routes|routes|8|CREATE TABLE routes (
     route_id TEXT PRIMARY KEY, 
     route_short_name TEXT, 
     route_long_name TEXT, 
     route_type INTEGER, 
     route_color TEXT 
) 
index|sqlite_autoindex_routes_1|routes|9| 
table|stop_times|stop_times|12|CREATE TABLE stop_times (
     stop_times_trip_id TEXT, 
     stop_times_stop_id TEXT, 
     stop_times_stop_sequence INTEGER, 
     stop_times_arrival_time TEXT, 
     stop_times_pickup_type INTEGER 
) 
table|stops|stops|13|CREATE TABLE stops (
     stop_id TEXT PRIMARY KEY, 
     stop_name TEXT, 
     stop_lat REAL, 
     stop_lon REAL 
) 
index|sqlite_autoindex_stops_1|stops|14| 
table|trips|trips|15|CREATE TABLE trips (
     trip_id TEXT PRIMARY KEY, 
     trip_service_id TEXT, 
     trip_route_id TEXT, 
     trip_headsign TEXT, 
     trip_direction_id INTEGER, 
     trip_shape_id TEXT 
) 
index|sqlite_autoindex_trips_1|trips|16| 

그리고 여기에 쿼리 계획이다 색인되어야한다 조회에 사용되는

2|0|0|SCAN TABLE stop_times (~33333 rows) 
2|1|1|SEARCH TABLE trips USING INDEX sqlite_autoindex_trips_1 (trip_id=?) (~1 rows) 
2|2|2|SEARCH TABLE calendar USING INDEX sqlite_autoindex_calendar_1 (calendar_service_id=?) (~1 rows) 
3|0|3|SCAN TABLE calendar_dates (~10000 rows) 
3|1|2|SEARCH TABLE calendar USING INDEX sqlite_autoindex_calendar_1 (calendar_service_id=?) (~1 rows) 
3|2|0|SEARCH TABLE stop_times USING AUTOMATIC COVERING INDEX (stop_times_stop_id=?) (~7 rows) 
3|3|1|SEARCH TABLE trips USING INDEX sqlite_autoindex_trips_1 (trip_id=?) (~1 rows) 
1|0|0|COMPOUND SUBQUERIES 2 AND 3 USING TEMP B-TREE (EXCEPT) 
4|0|3|SCAN TABLE calendar_dates (~10000 rows) 
4|1|2|SEARCH TABLE calendar USING INDEX sqlite_autoindex_calendar_1 (calendar_service_id=?) (~1 rows) 
4|2|0|SEARCH TABLE stop_times USING AUTOMATIC COVERING INDEX (stop_times_stop_id=?) (~7 rows) 
4|3|1|SEARCH TABLE trips USING INDEX sqlite_autoindex_trips_1 (trip_id=?) (~1 rows) 
0|0|0|COMPOUND SUBQUERIES 1 AND 4 USING TEMP B-TREE (UNION) 
+0

데이터베이스 스키마와 [쿼리 계획을 EXPLAIN]의 출력 (http://www.sqlite.org/eqp.html을 보여주십시오)를 사용합니다. –

+0

물론, 방금 내 게시물을 편집했습니다. 도움이되기를 바랍니다. – lost17

답변

0

열하지만 하나의 (하위)에 대한 쿼리에서는 테이블 당 둘 이상의 인덱스를 사용할 수 없습니다.

이 특정 쿼리를 들어, 다음과 같은 추가 인덱스는 도움이 될 것이다 :

CREATE INDEX some_index ON stop_times(
    stop_times_stop_id, 
    stop_times_arrival_time); 
CREATE INDEX some_other_index ON calendar_dates(
    calendar_dates_service_id, 
    calendar_dates_exception_type, 
    calendar_dates_date);