Имеется некое число, имеется таблица диапазонов. Соответственно нужно разбить это число согласно этих диапазонов, т.е. есть диапазоны: 0-200,200-300, свыше300, число 500 должно разбиться следующим образом: в первую группу 200, во-вторую 100, остатки 200 в третью. Таблица с диапазонами меняется в зависимости от настроения(. Раньше требовалось собирать данные без такой разбивки, а только по самому числу, входит оно в диапазон или нет, все добавлялось в запрос в цикле, а с такой разбивкой не соображу как это сделать. И как все это в макет вывести, т.к. количество колонок зависит от количества диапазонов
Прикрепленные файлы:
Книга1.xlsx
По теме из базы знаний
Найденные решения
(23) вот что имею ввиду:
ВЫБРАТЬ
0 КАК Начало,
200 КАК Окончание
ПОМЕСТИТЬ ВТ_Диапазоны
ОБЪЕДИНИТЬ ВСЕ
ВЫБРАТЬ
200,
300
ОБЪЕДИНИТЬ ВСЕ
ВЫБРАТЬ
300,
NULL
;
//////////////////////////////////////////////////////////// ////////////////////
ВЫБРАТЬ
500 КАК Число
ПОМЕСТИТЬ ВТ_Числа
ОБЪЕДИНИТЬ ВСЕ
ВЫБРАТЬ
700
ОБЪЕДИНИТЬ ВСЕ
ВЫБРАТЬ
235
ОБЪЕДИНИТЬ ВСЕ
ВЫБРАТЬ
75
;
//////////////////////////////////////////////////////////// ////////////////////
ВЫБРАТЬ
ВЫБОР
КОГДА 0 < Диапазоны.Начало
ТОГДА Диапазоны.Начало
ИНАЧЕ 0
КОНЕЦ КАК Начало,
ВЫБОР
КОГДА Диапазоны.Окончание < Числа.Число
ТОГДА Диапазоны.Окончание
ИНАЧЕ Числа.Число
КОНЕЦ КАК Окончание
ИЗ
ВТ_Числа КАК Числа
ЛЕВОЕ СОЕДИНЕНИЕ ВТ_Диапазоны КАК Диапазоны
ПО ((Диапазоны.Окончание Есть Null ИЛИ 0 < Диапазоны.Окончание)
И Числа.Число > Диапазоны.Начало)
ПоказатьОстальные ответы
Подписаться на ответы
Инфостарт бот
Сортировка:
Древо развёрнутое
Свернуть все
(9) Не любят запросы такую неопределенность. Я бы попробовал сделать так:
1. Во временную таблицу загружаем диапазоны (колонки (Н)ачало и (К)онец).
2. Добавил бы этой таблице колонку (П)оследняя. Соответственно, нужно определить максимальный диапазон для числа. Если (Ч)исло больше Н, то ставим ЛОЖЬ, если меньше Н, ставим НЕОПРЕДЕЛЕНО. Среди строк с П ЛОЖЬ находим максимальный К. Это и будет последняя, ставим ИСТИНА.
3. Далее к этой таблице присоединяем число по следующему алгоритму для П:
Если НЕОПРЕДЕЛЕНО, пропускаем - 0.
Если ИСТИНА, из Ч отнимаем Н - это остаток.
Если ЛОЖЬ, от К отнимаем Н - все числа диапазона входят в Ч.
Вроде так. Это теоретически, по-быстрому. Надо на практике смотреть, что в итоге получится для разных вариантов.
1. Во временную таблицу загружаем диапазоны (колонки (Н)ачало и (К)онец).
2. Добавил бы этой таблице колонку (П)оследняя. Соответственно, нужно определить максимальный диапазон для числа. Если (Ч)исло больше Н, то ставим ЛОЖЬ, если меньше Н, ставим НЕОПРЕДЕЛЕНО. Среди строк с П ЛОЖЬ находим максимальный К. Это и будет последняя, ставим ИСТИНА.
3. Далее к этой таблице присоединяем число по следующему алгоритму для П:
Если НЕОПРЕДЕЛЕНО, пропускаем - 0.
Если ИСТИНА, из Ч отнимаем Н - это остаток.
Если ЛОЖЬ, от К отнимаем Н - все числа диапазона входят в Ч.
Вроде так. Это теоретически, по-быстрому. Надо на практике смотреть, что в итоге получится для разных вариантов.
(1) По моему сценарию вот так можно сделать:
ВЫБРАТЬ
Диапазоны.Нач КАК Нач,
ВЫБОР
КОГДА Диапазоны.Кон = 0
ИЛИ Диапазоны.Кон ЕСТЬ NULL
ТОГДА &мЧисло + Диапазоны.Нач
ИНАЧЕ Диапазоны.Кон
КОНЕЦ КАК Кон,
ВЫБОР
КОГДА &мЧисло <= Диапазоны.Нач
ТОГДА НЕОПРЕДЕЛЕНО
КОГДА &мЧисло > Диапазоны.Нач
ТОГДА ЛОЖЬ
ИНАЧЕ ИСТИНА
КОНЕЦ КАК Последняя
ПОМЕСТИТЬ ВТ_Диапазоны
ИЗ
&Диапазоны КАК Диапазоны
;
//////////////////////////////////////////////////////////// ////////////////////
ВЫБРАТЬ
МАКСИМУМ(Диапазоны.Кон) КАК Кон
ПОМЕСТИТЬ ВТ_ДиапазоныМаксимум
ИЗ
ВТ_Диапазоны КАК Диапазоны
ГДЕ
Диапазоны.Последняя = ЛОЖЬ
;
//////////////////////////////////////////////////////////// ////////////////////
ВЫБРАТЬ
ВТ_Диапазоны.Нач КАК Нач,
ВТ_Диапазоны.Кон КАК Кон,
ВЫБОР
КОГДА ВТ_Диапазоны.Кон = ВТ_ДиапазоныМаксимум.Кон
ТОГДА ИСТИНА
ИНАЧЕ ВТ_Диапазоны.Последняя
КОНЕЦ КАК Последняя
ПОМЕСТИТЬ ВТ_ДиапазоныРаспр
ИЗ
ВТ_Диапазоны КАК ВТ_Диапазоны
ЛЕВОЕ СОЕДИНЕНИЕ ВТ_ДиапазоныМаксимум КАК ВТ_ДиапазоныМаксимум
ПО (ИСТИНА)
;
//////////////////////////////////////////////////////////// ////////////////////
ВЫБРАТЬ
ВТ_ДиапазоныРаспр.Нач КАК Нач,
ВТ_ДиапазоныРаспр.Кон КАК Кон,
ВТ_ДиапазоныРаспр.Последняя КАК Последняя,
ВЫБОР
КОГДА ВТ_ДиапазоныРаспр.Последняя = НЕОПРЕДЕЛЕНО
ТОГДА 0
КОГДА ВТ_ДиапазоныРаспр.Последняя = ИСТИНА
ТОГДА &мЧисло - ВТ_ДиапазоныРаспр.Нач
ИНАЧЕ ВТ_ДиапазоныРаспр.Кон - ВТ_ДиапазоныРаспр.Нач
КОНЕЦ КАК Разбивка
ИЗ
ВТ_ДиапазоныРаспр КАК ВТ_ДиапазоныРаспр
Показать
Сдается мне, что это типа нарастающего итога, только нарастающий итог вычитается из числа. Решается стандартной "треугольной" выборкой, когда из значения вычитается сумма диапазонов строки это "треугольной" таблицы.
Т.е. что-то типа
Где а - это исходная таблица с числом, которое нужно раздербанить по диапазонам, ну а вторая таблица - это диапазоны.
В общем тут все условно и нужно смотреть на данные.
Дисклеймер: цель сообщения не дать ответ, а навести на мысль.
Т.е. что-то типа
sel ect
where t.a - sum(d.b) > 0 then t.a - sum(d.b) else 0 end as field0
fr om t, d
where t.a > d.b
Где а - это исходная таблица с числом, которое нужно раздербанить по диапазонам, ну а вторая таблица - это диапазоны.
В общем тут все условно и нужно смотреть на данные.
Дисклеймер: цель сообщения не дать ответ, а навести на мысль.
почему в примере 500 разбиваеться на 200, 100, 200, а не на 200, 300??
а по существу, то можно что-то придумать на подобии распределения реализуемого товара между партиями в запросе
диапазон - это партия
таблица с числами - это товар
или что-то типа как в (13) как высчитываються итоги в запросе, когда береться таблица начальный остаток и таблица оборотов и для каждой строки оборота высчитываються данные... в этом случаи нужно диапазон представить как обороты расход, а таблица с числами как начальный остаток
а по существу, то можно что-то придумать на подобии распределения реализуемого товара между партиями в запросе
диапазон - это партия
таблица с числами - это товар
или что-то типа как в (13) как высчитываються итоги в запросе, когда береться таблица начальный остаток и таблица оборотов и для каждой строки оборота высчитываються данные... в этом случаи нужно диапазон представить как обороты расход, а таблица с числами как начальный остаток
Под задачей "разбить число согласно диапазонов" видимо подразумевается следующее:
Задана таблица диапазонов, есть таблица чисел предположительно задающие диапазоны от 0 до "число". Нужно найти пересечение диапазонов этих двух таблиц.
Решается банальным соединением двух таблиц, с проверкой на пересечение диапазонов, где диапазоны будут соответственно с наибольшей из нижних границ и с наименьшей из верхних.
Задана таблица диапазонов, есть таблица чисел предположительно задающие диапазоны от 0 до "число". Нужно найти пересечение диапазонов этих двух таблиц.
Решается банальным соединением двух таблиц, с проверкой на пересечение диапазонов, где диапазоны будут соответственно с наибольшей из нижних границ и с наименьшей из верхних.
(23) вот что имею ввиду:
ВЫБРАТЬ
0 КАК Начало,
200 КАК Окончание
ПОМЕСТИТЬ ВТ_Диапазоны
ОБЪЕДИНИТЬ ВСЕ
ВЫБРАТЬ
200,
300
ОБЪЕДИНИТЬ ВСЕ
ВЫБРАТЬ
300,
NULL
;
//////////////////////////////////////////////////////////// ////////////////////
ВЫБРАТЬ
500 КАК Число
ПОМЕСТИТЬ ВТ_Числа
ОБЪЕДИНИТЬ ВСЕ
ВЫБРАТЬ
700
ОБЪЕДИНИТЬ ВСЕ
ВЫБРАТЬ
235
ОБЪЕДИНИТЬ ВСЕ
ВЫБРАТЬ
75
;
//////////////////////////////////////////////////////////// ////////////////////
ВЫБРАТЬ
ВЫБОР
КОГДА 0 < Диапазоны.Начало
ТОГДА Диапазоны.Начало
ИНАЧЕ 0
КОНЕЦ КАК Начало,
ВЫБОР
КОГДА Диапазоны.Окончание < Числа.Число
ТОГДА Диапазоны.Окончание
ИНАЧЕ Числа.Число
КОНЕЦ КАК Окончание
ИЗ
ВТ_Числа КАК Числа
ЛЕВОЕ СОЕДИНЕНИЕ ВТ_Диапазоны КАК Диапазоны
ПО ((Диапазоны.Окончание Есть Null ИЛИ 0 < Диапазоны.Окончание)
И Числа.Число > Диапазоны.Начало)
Показать
Для получения уведомлений об ответах подключите телеграм бот:
Инфостарт бот