2016-04-11 2 views
2

У меня есть эта структура таблицы Дневник:Как получить MAX (Час) и MIN (Час) для каждого дня в этом запросе?

CREATE TABLE Diary 
(
    [IdDiary] bigint, 
    [IdDay] numeric(18,0) 
); 

INSERT INTO Diary ([IdDiary], [IdDay]) 
values 
(51, 1), 
(52, 2), 
(53, 5); 

И эту другую структуру таблицы DiaryTimetable:

CREATE TABLE DiaryTimetable 
(
    [IdDiary] bigint, 
    [Hour] varchar(50) 
); 

    INSERT INTO DiaryTimetable ([IdDiary], [Hour]) 
VALUES 
    (51, '09:00'), 
    (51, '09:30'), 
    (51, '10:00'), 
    (51, '10:30'), 
    (51, '11:00'), 
    (51, '11:30'), 
    (52, '11:00'), 
    (52, '11:30'), 
    (52, '12:00'), 
    (52, '12:30'), 
    (52, '13:00'), 
    (52, '13:30'), 
    (53, '15:00'), 
    (53, '15:30'), 
    (53, '16:00'), 
    (53, '16:30'); 

В таблице Дневник содержит IdDiary и IdDay это количество дней, например:

Monday --> 1 
Tuesday --> 2 
Wednesday --> 3 
Thursday --> 4 
Friday --> 5 
Saturday --> 6 
Sunday --> 7 

Таблица DiaryTimetable содержит идиперию и час. Я хочу получить максимальный час и мин. Час в таблице. DiaryTimetable для каждого дня отображается в таблице дневника. Если я поставлю этот запрос, результат будет равен только максимальному часу и минутному часу для всего запроса:

select MAX(Hour), MIN(Hour) from DiaryTimetable 
inner join Diary on 
DiaryTimetable.IdDiary = Diary.IdDiary 

в результате очист мне нужно будет что-то вроде этого:

IdDiary IdDay Min Hour Max Hour 
----- ----- -------- --------- 
51  1  09:00  11:30 
52  2  11:00  13:30 
53  5  15:00  16:30 

Как я могу получить это, спасибо?

SQL FIDDLE DEMO HERE

+0

Так что в таблице 'Diary' имеется столбец' IdDiary'. Из его имени я понимаю, что это первичный ключ таблицы, однозначно идентифицирующий запись. (Вы должны добавить это в свой оператор 'CREATE TABLE'.) Таким образом,' IdDay' - это информация, принадлежащая 'IdDiary'. Следовательно, «Дневник» не содержит дневников, а дневных дней. Да? Не может быть двух записей для того же 'IdDiary' в этой таблице. Это верно? (Может быть, вы должны подумать о лучшем имени таблицы.) И для каждой такой записи вы предоставляете «DiaryTimetable», показывающий часы дневного дня. Да? –

+1

И почему вы храните час в виде строки? В чем причина использования «TIME», которая кажется подходящим типом? И почему вы держите день и время отдельно в двух таблицах, вместо того, чтобы иметь одну таблицу, просто содержащую дату-время? –

+0

Это всего лишь быстрый пример, мне нужно было знать, как он бежал, чтобы учиться. Благодарю. –

ответ

5

Вы используете GROUP BY пункт:

SELECT d.IdDiary, d.IdDay, MIN(Hour), MAX(Hour) 
FROM Diary AS d 
LEFT JOIN DiaryTimetable AS dt ON d.IdDiary = dt.IdDiary 
GROUP BY d.IdDiary, d.IdDay 

Demo here

+0

Благодарим вас за помощь ;-D –

2

Вам просто нужно добавить GROUP BY к вашему запросу:

SELECT Diary.IdDiary, Diary.IdDay, MAX(DT.Hour), MIN(DT.Hour) 
FROM DiaryTimetable AS DT 
INNER JOIN Diary ON 
DT.IdDiary = Diary.IdDiary 
GROUP BY Diary.IdDiary, Diary.IdDay 

Тогда MAX nd MIN команда использует значения из вашей таблицы дневников.

+0

Ваш код работает правильно, спасибо за вашу помощь :-) –

4

В вашем запросе вы пропустили Group by.

SELECT b.IdDiary,a.IdDay, MIN(b.Hour), MAX(b.hour) 
    from Diary A INNER JOIN DiaryTimetable B ON A.IdDiary=B.IdDiary 
    GROUP by B.IdDiary ,a.IdDay 
+0

Спасибо за вашу помощь :-) –

2

Как в комментарии вы говорите, что это всего лишь пример для вас, чтобы узнать, я хотел бы добавить еще один ответ.

Учитывая, что нет повторяющихся записей в Diary, его две колонки IdDiary и IdDay являются поля, которые вы хотите получить дополнительную информацию по телефону (в мин и макс час). Так что все, что вам нужно сделать, это получить эту информацию присоединились к таблице:

select 
    d.iddiary, 
    d.idday, 
    dt.min_hour, 
    dt.max_hour 
from diary d 
join 
(
    select 
    iddiary, 
    min(hour) as min_hour, 
    max(hour) as max_hour 
    from diarytimetable 
    group by iddiary 
) dt on dt.iddiary = d.iddiary; 

прилипание к этой технике имеет два преимущества:

  1. Вы очень ясно показывают в вашем выбрать то, что вы делаете и как таблицы связаны.
  2. Это работает с несколькими агрегатами из разных таблиц. Некоторые люди, особенно новички, склонны сначала присоединяться ко всем таблицам и только потом думать о том, как добраться до необходимых данных. Это может быть довольно хлопотно. Скажем, у вас есть таблица city, таблица park и таблица lake. Вы хотите знать, сколько озер и сумма парковой зоны в каждом городе. Как показано, вы присоединились к городам с подсчетом озера и суммой парка.Если вы сначала присоединились ко всем таблицам, у вас будет комбинация озер и парков, которые на самом деле не связаны друг с другом, и было бы сложно или невозможно отделить желаемые результаты от этой слякотной записки.
+0

Muchas gracias por su explicación, es fácil de entender; -D –

Смежные вопросы