У мене є два набори вимірювань Землі за супутниковими даними, кожен з полями часу (mjd - середня юліанська дата) та географічними положеннями (GeoPoint, просторовий), і я шукаю збіги між двома наборами, щоб їх час відповідав порогу 3 години (або .125 днів) та їх відстань в межах 200 км один від одного.
Я зробив індекси як для полів mjd, так і для просторових таблиць.
Коли я просто приєднуюся до обмеження часу, база даних обчислює 100 000 матчів за 8 секунд і обчислює відстані для всіх 100 000 матчів за той час. Запит виглядає так:
select top 100000 h.Time, m.Time, h.GeoPoint.STDistance(m.GeoPoint)/1000.0
from L2V5.dbo.header h join L2.dbo.MLS_Header m
on h.mjd between m.mjd-.125 and m.mjd+.125
option( table hint ( h, index(ix_MJD) ), table hint( m, index(ix_MJD) ) )
А виконаний план такий:
При сортуванні 9 відстаней були менше 200 км, тому є матчі. Проблема полягає в тому, що коли я додаю обмеження на відстань і запускаю це,
select top 10 h.Time, m.Time, h.GeoPoint.STDistance(m.GeoPoint)/1000.0
from L2V5.dbo.header h join L2.dbo.MLS_Header m
on h.mjd between m.mjd-.125 and m.mjd+.125
and h.GeoPoint.STDistance(m.GeoPoint)<200000
option( table hint ( h, index(ix_MJD) ), table hint( m, index(ix_MJD) ) )
воно проходить надовго. Очевидно, що за 8 секунд він міг знайти 100 000 матчів за часом, 9 з яких були менше 200 км, тож оптимізатор повинен намагатися щось неоптимальне. План виглядає подібним до вище з фільтром на відстані (я здогадуюсь).
Я можу змусити використовувати просторовий індекс за допомогою цього:
select top 5 h.Time, m.Time, h.GeoPoint.STDistance(m.GeoPoint)/1000.0
from L2V5.dbo.header h join L2.dbo.MLS_Header m
on h.GeoPoint.STDistance(m.GeoPoint)<200000
and h.mjd between m.mjd-.125 and m.mjd+.125
option( table hint ( h, index(ix_MJD), index(ix_GeoPoint) ), table hint( m, index(ix_MJD) ) )
після чого знадобиться 3 хвилини, щоб знайти 5 матчів.
Як я можу оптимізатору запитів використовувати спочатку пошук індексу MJD, а потім просторовий індекс другий (або це те, що він вже робить), і чи можна я допомогти йому, сказавши, скільки матчів очікувати? Якщо він може обчислити 100 000 матчів з відстанями за 8 секунд, що має 9 менше 200 км, чи не слід додавання просторового індексу зробити його швидшим, а не повільним?
Дякуємо за будь-які інші поради чи ідеї.
EDIT: Щоб відповісти на питання, як виглядає план без натяків, це (і це займе назавжди):
Можливо, варто також згадати, що в одній таблиці є майже 1М записів, а в іншій - 8М