2011-12-29 2 views
1

У меня возникли проблемы с формулировкой SQL для этой ситуации: Представьте, что в любое время на дороге есть несколько транспортных средств, Каждое из этих поездок находится в таблице поездок. Каждое транспортное средство регулярно посылает обновления своего текущего местоположения (широта, долгота)Как выбрать из 2 таблиц и получить наибольшее значение из одной таблицы?

Есть 2 таблицы: current_position

идентификатор | trip_id | update_time | lat | lon

поездки

ID | Статус

current_position имеет несколько обновлений для каждой поездки

мне нужно, чтобы получить результаты, имеющие trip_id, широта, долгота

для каждой поездки, которая имеет статус = «ВОЖДЕНИЙ» и должна иметь последние значения от current_position

Последнее значение Я имею в виду наивысшее значение update_time. Когда я попробовал GROUP BY, я получил отличные результаты, но результаты были не всегда последней позицией. Кажется, я не могу комбинировать порядок с помощью update_time DESC с GROUP BY trip_id

ответ

1

похоже, что вы хотите выбрать строку current_position с наибольшим значением update_time для данного trip_id. Вы можете сделать это с помощью подзапроса с использованием MAX.

Select * from current_position 
Where trip_id = @trip_id 
and update_time = (Select Max(update_time) from current_position where trip_id = @trip_id) 

Редактировать ... после публикации, я понимаю, что вам нужно соединение, чтобы получить все строки, где соответствующий статус отключения = «вождение». Я думаю, что это будет сделано (хотя я больше Sql Server, поэтому может быть небольшая разница с MySQL, о котором я не знаю).

Select * from current_position cp 
join trips t on cp.trip_id = t.id 
where t.status = 'Driving' 
and cp.update_time = (select Max(update_time) from current_position where trip_id = t.id) 
+0

Так что, если есть 300 поездок в настоящее время в ходе тогда будет 300 подзапросы в этом запросе? –

+0

производительность не должна быть проблемой для 300 возвращенных записей. Попробуй и посмотри. – nycdan

+0

DRapp делает хорошую точку. Вероятно, вы можете использовать Max (id) вместо Max (update_time) и получать лучшую производительность на больших таблицах. – nycdan

-1

С MySQL, группа без совокупного столбца даст вам первую строку для каждого отдельного значения, поэтому использовать группу с помощью после заказа по.

Это просто:

select trip_id, lat, lon 
from (select * from current_position 
     join trips on trips.id = current_position.id 
     where status = 'DRIVING' 
     order by trip_id, update_time desc) x 
group by trip_id 
+0

current_position не имеет статуса столбца, статус находится в таблице отключений –

+0

current_position не имеет столбца состояния ... –

+0

Спасибо, ребята, я исправил запрос :) – Bohemian

1

Начните с prequery по ID поездки и максимальное время, а затем вновь присоединиться к этой спине, основанный на самое последнее время. Тем не менее, если столбец идентификатора текущей позиции таблицы является столбцом автоматического увеличения, а update_time всегда будет больше, чем последний, в котором будет отображаться отчет, вместо этого я бы изменил max() времени на максимальное значение идентификатора текущей позиции таблица, как это было бы лучше всего на группе и индексе при присоединении после «PreQuery»

У меня также был бы указатель в таблице ваших поездок по статусу, чтобы сократить ваши результаты запроса. Когда ваша таблица будет построена, если вы начнете 10 000 поездок, и только 15 в настоящее время приводятся для доставки (или что-то еще), вы будете получать только те, которые активны 15, а не охватывают всю таблицу поездок.

select 
     cp2.* 
    from 
     (select t.id, 
       max(cp.update_time) as MostRecent 
      from 
       trips t 
       join current_position cp 
        on t.id = cp.trip_id 
      where 
       t.status = 'Driving' 
      group by 
       t.id) PreQuery 
     join current_position cp2 
     on PreQuery.id = cp2.trip_id 
     and PreQuery.MostRecent = cp2.update_time 
0

Другой способ:

SELECT 
    cp.* 
FROM 
     (SELECT id 
      FROM trips 
      WHERE status = 'DRIVING' 
     ) AS t 
    JOIN 
     current_position AS cp 
     ON 
     cp.id = 
     (SELECT cpm.id 
      FROM current_position AS cpm 
      WHERE cpm.trip_id = t.id 
      ORDER BY cpm.update_time DESC 
      LIMIT 1 
     ) 
Смежные вопросы