Sql: Optimizing BETWEEN clause

前端 未结 9 752
孤街浪徒
孤街浪徒 2021-02-06 07:38

I wrote a statement that takes almost an hour to run so I am asking help so I can get to do this faster. So here we go:

I am making an inner join of two tables :

<
相关标签:
9条回答
  • 2021-02-06 08:19

    Your SQL is equivalent to:

    select m.measure. m.time, 
         i.entry_time, i.exit_time
    from intervals i
        join measures m
            on m.time Between i.entry_time And i.exit_time  
    order by time asc
    

    The only thing I might suggest is making sure there's an index on m.Time. Then if that doesn't improve performance enough, try adding indices on i.Start_Time and i.End_Time as well

    0 讨论(0)
  • 2021-02-06 08:20

    Not knowing what database system and version, I'd say that (lack of) indexing and the join clause could be causing the problem.

    For every record in the measure table, you can have multiple records in the interval table (intervals.entry_time<=measures.time), and for every record in the interval table, you can have multiple records in measure (measures.time <=intervals.exit_time). the resulting one-to-many and many-to one relationships cause by the join means multiple table scans for each record. I doubt that Cartesian Product is the correct term, but it's pretty close.

    Indexing would definitely help, but it would help even more if you could find a better key to join the two tables. having the one-to-many relationships going in one direction only would definitely speed up the processing as it wouldn't have to scan each table/index twice for each record.

    0 讨论(0)
  • 2021-02-06 08:24

    The first thing I do is have your database tool generate an execution plan that you can view (this is "Control-L" in MSSQL, but I'm not sure how to do it in Oracle) - that will try to point out the slow parts and, depending on your Server/Editor, it may even recommend some basic indexes. Once you have an execution plan, you can look for any table scans of inner loop joins, both of which are really slow - indexes can help with table scans, and you can add additional join predicates to help alleviate loop joins.

    My guess would be the MEASURES needs an index on the TIME column, and you can include the MEASURE column as well to speed lookups. Try this:

    CREATE INDEX idxMeasures_Time ON Measures ([Time]) INCLUDES (Measure)
    

    Also, though this won't change your execution plan or speed up your query, it may make your join clause a bit easier read:

    ON measures.time BETWEEN intervals.entry_time AND intervals.exit_time
    

    This just combines your two <= and >= into a single statement.

    0 讨论(0)
提交回复
热议问题