Mysql
 sql >> Baza danych >  >> RDS >> Mysql

Filtrowanie zestawu wyników zapytania MySQL w celu uzyskania wielu wystąpień w określonym czasie

Jeśli chcemy odfiltrować wiersze, w których nie ma co najmniej czterech poprzedzających wierszy w ciągu ostatnich 60 sekund, zakładając, że dateTimeOrigination jest typem całkowitym, 32-bitowym znacznikiem czasu w stylu unix, możemy zrobić coś takiego:

SELECT FROM_UNIXTIME(r.dateTimeOrigination) AS dateTimeOrigination
     , r.callingPartyNumber
     , r.originalCalledPartyNumber
     , r.finalCalledPartyNumber
     , r.duration
     , r.origDeviceName
     , r.destDeviceName
  FROM cdr_records r
 WHERE r.dateTimeOrigination >= UNIX_TIMESTAMP('2016-05-20')
   AND r.dateTimeOrigination  < UNIX_TIMESTAMP('2016-05-21')
   AND r.callingPartyNumber NOT LIKE 'b00%'
   AND r.originalCalledPartyNumber NOT LIKE 'b00%'
   AND r.finalCalledPartyNumber NOT LIKE 'b00%'

   AND ( SELECT COUNT(1)
           FROM cdr_records c
          WHERE c.originalCalledPartyNumber = r.originalCalledPartyNumber
            AND c.dateTimeOrigination       > r.dateTimeOrigination - 60
            AND c.dateTimeOrigination      <= r.dateTimeOrigination
       ) > 4

 ORDER
    BY r.originalCalledPartyNumber
     , r.dateTimeOrigination

UWAGA:Aby uzyskać wydajność, wolimy mieć predykaty na gołych kolumnach.

W formie takiej jak ta, z kolumną owiniętą w wyrażenie:

 WHERE FROM_UNIXTIME(r.dateTimeOrigination) LIKE '2016-05-20%'

MySQL oceni funkcję dla każdego w tabeli, a następnie porównaj zwrot z funkcji z literałem.

W takim formularzu:

 WHERE r.dateTimeOrigination >= UNIX_TIMESTAMP('2016-05-20')
   AND r.dateTimeOrigination  < UNIX_TIMESTAMP('2016-05-21')

MySQL oceni wyrażenia po prawej stronie jeden czas, jak litery . Co pozwala MySQL na efektywne wykorzystanie operacji skanowania zakresu na odpowiednim indeksie.

KONTYNUACJA

Aby uzyskać najlepszą wydajność zewnętrznego zapytania, najlepszym indeksem byłby prawdopodobnie indeks z wiodącą kolumną dateTimeOrigination, najlepiej zawierający

... ON cdr_records (dateTimeOrigination
    ,callingPartyNumber,originalCalledPartyNumber,finalCalledPartyNumber)

Aby uzyskać najlepszą wydajność, indeks pokrywający, aby uniknąć wyszukiwania stron w tabeli podstawowej. Na przykład:

... ON cdr_records (dateTimeOrigination
    ,callingPartyNumber,originalCalledPartyNumber,finalCalledPartyNumber
    ,duration,origDeviceName,destDeviceName)

W związku z tym spodziewamy się, że EXPLAIN wyświetli „Korzystanie z indeksu”.

W przypadku skorelowanego podzapytania chcielibyśmy mieć indeks z wiodącymi kolumnami w następujący sposób:

... ON cdr_records (originalCalledPartyNumber,dateTimeOrigination)

Zdecydowanie polecam spojrzeć na dane wyjściowe z EXPLAIN, aby zobaczyć, których indeksów MySQL używa do zapytania.




  1. Database
  2.   
  3. Mysql
  4.   
  5. Oracle
  6.   
  7. Sqlserver
  8.   
  9. PostgreSQL
  10.   
  11. Access
  12.   
  13. SQLite
  14.   
  15. MariaDB
  1. MySQL LEFT JOIN Wiele warunków

  2. czy istnieje funkcja mysql do dekodowania jednostek html?

  3. Jak sprawdzić, czy kolumna jest pusta lub null w MySQL?

  4. Importuj plik CSV, aby zaktualizować tylko jedną kolumnę w tabeli

  5. Jak zapisać wynik zapytania MySQL w pliku .CSV?