С Новым годом! Форум программистов, компьютерный форум, киберфорум
Microsoft SQL Server
Войти
Регистрация
Восстановить пароль
Карта форума Темы раздела Блоги Сообщество Поиск Заказать работу  
 
Рейтинг 4.93/15: Рейтинг темы: голосов - 15, средняя оценка - 4.93
7 / 7 / 7
Регистрация: 26.04.2015
Сообщений: 220
1

Как из таблицы со списком, когда аудитории заняты, собрать таблицу со списком когда они свободны

22.03.2017, 17:10. Показов 2801. Ответов 12

Author24 — интернет-сервис помощи студентам
Есть таблица:
ID НомерАудитории Дата ВремяНачалааЗанятия ВремяКонца занятия
1 123 22.03.2017 12:00 14:00
2 123 22.03.2017 16:00 18:00
3 321 22.03.2017 12:00 14:00
4 321 22.03.2017 14:00 16:00
5 321 22.03.2017 16:00 18:00
...

В таблицу есть следующие триггеры:
- на одно время нельзя один кабинет бронировать
- время начала раньше времени конца
- заполнять твблицу можно не чем за 10 минут до начала занятия в какойто аудитории
- дальше чем на 2 месяца записывать нельзя
- занятия что идут или уже закончились из таблицы удалять нельзя
- Кабинет можно забронировать на время с 8:00 до 22:00
- ну и кабинеты связаны с таблицей "Список кабинетов" (не ключем, так чтобы и можно было удалить кабинет, а запись в таблице истории занятости оставалась).

Вопрос: Вводится дата, на эту дату надо найти все свободные кабинеты, т.е. из примера получим:
НомерАудитории Дата СвободенС СвободенДо
123 22.03.2017 8:00 12:00
123 22.03.2017 14:00 16:00
123 22.03.2017 18:00 22:00
321 22.03.2017 8:00 12:00
321 22.03.2017 18:00 22:00

Как отсортировать по дате я понимаю, а как найти время свободное?

Я думала что можно найти ID каждого кабинета на определенную дату, но как дальше действовать чет не придумаю. Может есть какие варианты полегче?
0
Лучшие ответы (1)
IT_Exp
Эксперт
87844 / 49110 / 22898
Регистрация: 17.06.2006
Сообщений: 92,604
Блог
22.03.2017, 17:10
Ответы с готовыми решениями:

Вывести две таблицы со списком городов и одну со списком их координат
помогите пожалуйста написать макрос.функцией ВПР не пользоваться.такое условие. задача такая: из...

На побережье три маяка; определить, когда они одновременно отключатся и когда одновременно загорятся
«На побережье три маяка. Первый светит в течение 3-х секунд, затем он отключается на 3 секунды....

Как реализовать работу со списком строк и списком цифр в классе List?
Добрый день! Проблема такая Есть класс-список: #include "stdafx.h" #include <iostream>...

Как сделать цикл со списком имен файлов и списком для их переименования
Здравствуйте, прошу помощи уважаемые форумчане. Есть файлы с определенными названиями в разных...

12
1040 / 856 / 335
Регистрация: 08.12.2016
Сообщений: 3,283
22.03.2017, 17:26 2
занимать можно строго только в 8, 10, 12, 14, 16, 18 и 20.00 на 2/4/6/8/12/14 часов?

Добавлено через 3 минуты
ВремяХХХзанятий - какой тип данных
0
7 / 7 / 7
Регистрация: 26.04.2015
Сообщений: 220
22.03.2017, 17:27  [ТС] 3
YuryK, нет можно в любое вреся с 8:00 до 22:00 время длительности не ограничено
0
1040 / 856 / 335
Регистрация: 08.12.2016
Сообщений: 3,283
22.03.2017, 17:29 4
Цитата Сообщение от YuryK Посмотреть сообщение
ВремяХХХзанятий - какой тип данных
все ещё интересует
0
7 / 7 / 7
Регистрация: 26.04.2015
Сообщений: 220
22.03.2017, 17:29  [ТС] 5
Цитата Сообщение от YuryK Посмотреть сообщение
ВремяХХХзанятий - какой тип данных
не поняла?

ID - автоинкримент
номерКабинета - smallint
дата - date
время начала занятия - time
время конца занятия - time

Можно поменять, если от этого будет легче считать.
Я вообще не могу придумать логику по которой можно искать. Мне бы итерацию каждой строки, типо как у массивов
0
1040 / 856 / 335
Регистрация: 08.12.2016
Сообщений: 3,283
22.03.2017, 17:37 6
Цитата Сообщение от Ruta Посмотреть сообщение
Я вообще не могу придумать логику по которой можно расчитывать
Такая пойдет?

выбрать с 8.00 до первого занятия, если первое занятие позже 8.00
UNION ALL
выбрать с конца последнего занятия до 22.00 если заканчивается раньше 22.00
UNION ALL
от конца занятия до начала следующего, если они не совпали
UNION ALL
кабинеты вовсе не попавшие в заявку
1
7 / 7 / 7
Регистрация: 26.04.2015
Сообщений: 220
22.03.2017, 17:46  [ТС] 7
YuryK, да, но как сравнивать строки в таблице
Цитата Сообщение от YuryK Посмотреть сообщение
выбрать с 8.00 до первого занятия, если первое занятие позже 8.00)
UNION ALL
выбрать с конца последнего занятия до 20.00 если заканчивается раньше 20.00
UNION ALL
Цитата Сообщение от YuryK Посмотреть сообщение
кабинеты вовсе не попавшие в заявку
это я поняла как реализовывать, а
Цитата Сообщение от YuryK Посмотреть сообщение
от конца занятия до начала следующего, если они не совпали
UNION ALL
не совсем понимаю.
Я сразу не написала, наверное зря,
записи же в таблице могут идти так:
Есть таблица:
ID НомерАудитории Дата ВремяНачалааЗанятия ВремяКонца занятия
1 123 22.03.2017 12:00 14:00
2 123 22.03.2017 16:00 18:00
3 321 22.03.2017 12:00 14:00
4 321 22.03.2017 14:00 16:00
5 321 22.03.2017 16:00 18:00

а могут так:
Есть таблица:
ID НомерАудитории Дата ВремяНачалааЗанятия ВремяКонца занятия
1 123 22.03.2017 12:00 14:00
2 321 22.03.2017 16:00 18:00
3 321 22.03.2017 14:00 16:00
4 321 22.03.2017 12:00 14:00
5 123 22.03.2017 16:00 18:00
0
1040 / 856 / 335
Регистрация: 08.12.2016
Сообщений: 3,283
22.03.2017, 18:12 8
Лучший ответ Сообщение было отмечено Ruta как решение

Решение

как то так
T-SQL
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
DECLARE @Date datetime SET @Date = '20170322'
 
DECLARE @TimeFrom datetime, @TimeTo datetime
SET @TimeFrom = 0
SET @TimeTo =0
SET @TimeFrom  = DATEADD(hour, 8, @TimeFrom)
SET @TimeTo  = DATEADD(hour, 22, @TimeFrom)
 
 
SELECT НомерАудитории, @TimeFrom TimeFrom, MIN(ВремяНачалааЗанятия) TimeTo
FROM [Есть таблица] 
WHERE Дата  = @Date 
GROUP BY НомерАудитории
HAVING MIN(ВремяНачалааЗанятия) > @TimeFrom
 
UNION ALL
 
SELECT НомерАудитории, MAX([ВремяКонца занятия]), @TimeTo  
FROM [Есть таблица] 
WHERE Дата  = @Date 
GROUP BY НомерАудитории
HAVING MAX([ВремяКонца занятия]) < @TimeTo
 
UNION ALL
 
SELECT 
  t1.НомерАудитории, t1.[ВремяКонца занятия], MIN(t2.ВремяНачалааЗанятия)
FROM 
  [Есть таблица] t1
  JOIN [Есть таблица] t2 ON 
    t1.НомерАудитории = t2.НомерАудитории AND
    t2.ВремяНачалааЗанятия >= t1.[ВремяКонца занятия]
GROUP BY 
  t1.НомерАудитории, t1.[ВремяКонца занятия], MIN(t2.ВремяНачалааЗанятия)  
HAVING 
  MIN(t2.ВремяНачалааЗанятия) > t1.[ВремяКонца занятия]
 
UNION ALL
 
SELECT
  r.НомерАудитории ,  @TimeFrom, @TimeTo
FROM
  [Список кабинетов] r 
  LEFT JOIN [Есть таблица] t ON r.НомерАудитории = t.НомерАудитории
WHERE
   t.НомерАудитории IS NULL
1
7 / 7 / 7
Регистрация: 26.04.2015
Сообщений: 220
22.03.2017, 20:06  [ТС] 9
Цитата Сообщение от YuryK Посмотреть сообщение
T-SQL
1
2
3
4
5
6
DECLARE @Date datetime SET @Date = '20170322'
DECLARE @TimeFrom datetime, @TimeTo datetime
SET @TimeFrom = 0
SET @TimeTo =0
SET @TimeFrom *= DATEADD(hour, 8, @TimeFrom)
SET @TimeTo *= DATEADD(hour, 22, @TimeFrom)
Если я буду использовать вместо datetime data и time, результат изменится (кроме присвоения им даты и времени)?

Цитата Сообщение от YuryK Посмотреть сообщение
T-SQL
1
2
3
4
5
6
7
8
9
10
11
SELECT 
* t1.НомерАудитории, t1.[ВремяКонца занятия], MIN(t2.ВремяНачалааЗанятия)
FROM 
* [Есть таблица] t1
* JOIN [Есть таблица] t2 ON 
* * t1.НомерАудитории = t2.НомерАудитории AND
* * t2.ВремяНачалааЗанятия >= t1.[ВремяКонца занятия]
GROUP BY 
* t1.НомерАудитории, t1.[ВремяКонца занятия], MIN(t2.ВремяНачалааЗанятия) */*ругается на эту строку*/
HAVING 
* MIN(t2.ВремяНачалааЗанятия) > t1.[ВремяКонца занятия]
Нельзя использовать статистический или вложенный запрос в выражении, используемом для списка GROUP BY предложения GROUP BY.
Хотела сделать как выше:
Цитата Сообщение от YuryK Посмотреть сообщение
T-SQL
1
MIN(ВремяНачалааЗанятия) TimeTo
начал ругаться на переменную: Недопустимое имя столбца.
0
3548 / 2122 / 752
Регистрация: 02.06.2013
Сообщений: 5,150
22.03.2017, 21:33 10
T-SQL
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
set language russian;
 
declare @t table(НомерАудитории int, Дата date, СвободенС time, СвободенДо time);
 
insert into @t
values
(123, '22.03.2017', '9:00', '12:00'),
(123, ' 22.03.2017', '14:00', '16:00'),
(123, ' 22.03.2017', '18:00', '21:00'),
(321, ' 22.03.2017', '8:00', '12:00'),
(321, ' 22.03.2017', '18:00', '22:00');
 
with t1 as
(
 select
  НомерАудитории, Дата, СвободенС, СвободенДо,
  min(СвободенС) over (partition by НомерАудитории, Дата) as СвободенС_min,
  max(СвободенДо) over (partition by НомерАудитории, Дата) as СвободенДо_max
 from
  @t
),
t2 as
(
 select
  t1.НомерАудитории, t1.Дата, b.t,
  row_number() over (partition by t1.НомерАудитории, t1.Дата order by b.t) as rn
 from
  t1 cross apply
  (
   select a.t from (values ('08:00'), ('08:00')) a(t) where t1.СвободенС = t1.СвободенС_min and t1.СвободенС_min <> '08:00'
   union all
   select t1.СвободенС
   union all
   select t1.СвободенДо
   union all
   select a.t from (values ('22:00'), ('22:00')) a(t) where t1.СвободенДо = t1.СвободенДо_max and t1.СвободенДо_max <> '22:00'
  ) b(t)
)
select
 x1.НомерАудитории, x1.Дата, x1.t, x2.t
from
 t2 x1 join
 t2 x2 on x2.НомерАудитории = x1.НомерАудитории and x2.Дата = x1.Дата and x2.rn = x1.rn + 1
where
 x1.rn % 2 = 0 and
 x1.t < x2.t;
1
1040 / 856 / 335
Регистрация: 08.12.2016
Сообщений: 3,283
23.03.2017, 00:31 11
Цитата Сообщение от Ruta Посмотреть сообщение
*/*ругается на эту строку*/
, MIN ... - лишнее (я запрос писал в блокноте, поэтому работоспособность с колес невозможна)

Цитата Сообщение от Ruta Посмотреть сообщение
Если я буду использовать вместо datetime data и time
наверное, я с этими типам данных ещё не работал
1
7 / 7 / 7
Регистрация: 26.04.2015
Сообщений: 220
23.03.2017, 12:03  [ТС] 12
Цитата Сообщение от Ruta Посмотреть сообщение
GROUP BY
* t1.НомерАудитории, t1.[ВремяКонца занятия], t2.ВремяНачалааЗанятия
переспрошу на всякий случай, так?
0
1040 / 856 / 335
Регистрация: 08.12.2016
Сообщений: 3,283
23.03.2017, 12:05 13
только 2 атрибута
Цитата Сообщение от YuryK Посмотреть сообщение
GROUP BY
* t1.НомерАудитории, t1.[ВремяКонца занятия]
1
23.03.2017, 12:05
BasicMan
Эксперт
19315 / 2622 / 84
Регистрация: 17.02.2009
Сообщений: 10,364
Блог
23.03.2017, 12:05
Помогаю со студенческими работами здесь

Компьютер работает только когда не все слоты ОЗУ заняты
Хай всем еще раз! Теперь проблема в следующем : у меня на компе стоит 4 карточки озу , но комп...


Искать еще темы с ответами

Или воспользуйтесь поиском по форуму:
13
Ответ Создать тему
КиберФорум - форум программистов, компьютерный форум, программирование
Powered by vBulletin
Copyright ©2000 - 2025, CyberForum.ru