sql >> Databáze >  >> RDS >> Mysql

Porovnání období

Toto je klasický problém a ve skutečnosti je jednodušší, když obrátíte logiku.

Dovolte mi uvést příklad.

Zde zveřejním jedno časové období a všechny různé varianty jiných období, které se nějakým způsobem překrývají.

           |-------------------|          compare to this one
               |---------|                contained within
           |----------|                   contained within, equal start
                   |-----------|          contained within, equal end
           |-------------------|          contained within, equal start+end
     |------------|                       not fully contained, overlaps start
                   |---------------|      not fully contained, overlaps end
     |-------------------------|          overlaps start, bigger
           |-----------------------|      overlaps end, bigger
     |------------------------------|     overlaps entire period

na druhou stranu mi dovolte zveřejnit všechny, které se nepřekrývají:

           |-------------------|          compare to this one
     |---|                                ends before
                                 |---|    starts after

Pokud tedy srovnání jednoduše zredukujete na:

starts after end
ends before start

pak najdete všechna, která se nepřekrývají, a pak najdete všechna neshodná období.

Pro váš poslední příklad NOT IN LIST můžete vidět, že odpovídá těmto dvěma pravidlům.

Budete se muset rozhodnout, zda jsou následující období V nebo MIMO vaše rozsahy:

           |-------------|
   |-------|                       equal end with start of comparison period
                         |-----|   equal start with end of comparison period

Pokud má vaše tabulka sloupce nazvané range_end a range_start, zde je několik jednoduchých SQL pro načtení všech odpovídajících řádků:

SELECT *
FROM periods
WHERE NOT (range_start > @check_period_end
           OR range_end < @check_period_start)

Všimněte si NE tam. Protože dvě jednoduchá pravidla najde všechny neodpovídající řádky, jednoduché NOT to obrátí a řekne:pokud to není jeden z neodpovídajících řádků, musí to být jeden z odpovídajících .

Když zde použijete jednoduchou reverzní logiku, abyste se zbavili NOT a skončíte s:

SELECT *
FROM periods
WHERE range_start <= @check_period_end
      AND range_end >= @check_period_start


  1. Jak rychle napsat Select Query v SQL Server - SQL Server / TSQL Tutorial část 108

  2. T-SQL rozdělený řetězec na základě oddělovače

  3. Stromová struktura v SQL v Oracle. Jak zobrazit strom, podřízené uzly a nadřazené uzly v SQL Oracle

  4. Rails 4 session.id občas nula