Уважаемые знатоки! Подскажите, что Вы думаете поп поводу данной задачки...
Задача
Есть периодический регистр сведений «Показания спидометра» с измерением «Авто» и ресурсом «Пробег, км» со следующими данными:
1. 01/01/2012 Авто1 100.00
2. 02/01/2012 Авто1 500.00
3. 03/01/2012 Авто1 50.00
4. 04/01/2012 Авто1 400.00
5. 06/01/2012 Авто1 100.00
Как видим показания растут, но спидометр периодически может обнуляться. Необходимо одним запросом (вложенные запросы и временные таблицы допускаются) получение общего пробега за произвольный период.
Обнуление счетчика может происходить в любой день.
Правильным ответом по приведенному примеру будет пробег 1000 км за весь период.
При решении задачи учитывать что автомобилей может быть несколько…
А в чем проблема-то, непонятно...
| ВЫБРАТЬ * ИЗ РегистрыСведений.ПоказанияСпидометра КАК Т ГДЕ Т.Период МЕЖДУ НАЧАЛОПЕРИОДА(&НачалоПериода, ДЕНЬ) И КОНЕЦПЕРИОДА(&КонецПериода,ДЕНЬ) И Т.Автомобиль В(&СписокАвтомоиблей)
(2) Проблема в расчете пробега после обнуления (запросом)
ТС. Ключевое выражение для поиска "Нарастающий итог в запросе".
А так - левое соединение таблицыс собой по периоду
| ВЫБРАТЬ * ИЗ РегистрыСведений.ПоказанияСпидометра КАК Т ГДЕ Т.Период МЕЖДУ НАЧАЛОПЕРИОДА(&НачалоПериода, ДЕНЬ) И КОНЕЦПЕРИОДА(&КонецПериода,ДЕНЬ) И Т.Автомобиль В(&СписокАвтомоиблей)
! | Правила, п.13 |
На первый взгляд, задача некорректна. Пример:
День Пробег
1 100
2 200
(здесь прошло обнуление)
3 210
(в первый день наездили 100, во второй тоже 100, дальше обнулили и проехали 210)
Т.е. по предложенным данным невозможно отследить ситуацию, когда в день обнуления машина наездила столько же или чуть больше, чем накопилось до того.
Вывод: нужно добавить информацию, в какие дни было обнуление. Тогда будет возможно решить такую задачу.
Переделать на регистр оборотов.
Когда вводим документ документ рассчитывает было обнуление или нет. И проводим не показания счетчика а прирост пробега.
Или на тот-же регистр сведений добавить ещё один ресурс - "прирост пробега".
ну если только математически ... то главное - половить перепады(пары значений) с большего значения на меньшее и взять из пары -бОльшее. потом просумировать бОльшие зн. + последнее.
Как это языком запроса понятия не имею.
остальные значения - не нужны.
Кое что уже получается... запрос такой...
ВЫБРАТЬ
ПоказанияСпидометра.Период,
ПоказанияСпидометра.Авто,
ПоказанияСпидометра.Пробег
ПОМЕСТИТЬ ВТдвижения
ИЗ
РегистрСведений.ПоказанияСпидометра КАК ПоказанияСпидометра
;
////////////////////////////////////////////////////////////////////////////////
ВЫБРАТЬ
Движения.Период КАК Период,
Движения.Авто КАК Авто,
Движения.Пробег КАК Пробег,
СУММА(ТеЖеДвижения.Пробег) КАК ПробегНарастающийИтог
ИЗ
ВТдвижения КАК Движения
ЛЕВОЕ СОЕДИНЕНИЕ ВТдвижения КАК ТеЖеДвижения
ПО Движения.Период >= ТеЖеДвижения.Период
ГДЕ
Движения.Период МЕЖДУ НАЧАЛОПЕРИОДА(&НачалоПериода, ДЕНЬ) И КОНЕЦПЕРИОДА(&КонецПериода, ДЕНЬ)
И Движения.Авто В(&СписокАвтомоиблей)
СГРУППИРОВАТЬ ПО
Движения.Период,
Движения.Авто,
Движения.Пробег
УПОРЯДОЧИТЬ ПО
Авто,
Период
Вот так 1С учит новых программистов -
хранение пробега в РС (вместо оборотов/остатков), а дальше соорудите аццкий запрос к базе, увеличивающий таблицу выборки в геометрической прогрессии.
Дебильная постановка задачи, если чесно.
На коленке где-то так:
ВЫБРАТЬ
ПоказанияСпидометра.Авто,
ПоказанияСпидометра.Период КАК ТекПериод,
ПоказанияСпидометра.Спидометр КАК ТекСпидометр,
МАКСИМУМ(ПоказанияСпидометраПредыдущие.Период) КАК ПредПериод
ПОМЕСТИТЬ Таб1
ИЗ
РегистрСведений.ПоказанияСпидометра КАК ПоказанияСпидометра
ЛЕВОЕ СОЕДИНЕНИЕ РегистрСведений.ПоказанияСпидометра КАК ПоказанияСпидометраПредыдущие
ПО ПоказанияСпидометра.Период > ПоказанияСпидометраПредыдущие.Период
И ПоказанияСпидометра.Авто = ПоказанияСпидометраПредыдущие.Авто
СГРУППИРОВАТЬ ПО
ПоказанияСпидометра.Период,
ПоказанияСпидометра.Авто,
ПоказанияСпидометра.Спидометр
;
////////////////////////////////////////////////////////////////////////////////
ВЫБРАТЬ
Таб1.Авто,
Таб1.ТекПериод КАК ТекПериод,
Таб1.ТекСпидометр,
ЕСТЬNULL(ПоказанияСпидометра.Спидометр, 0) КАК ПредСпидометр,
ВЫБОР
КОГДА Таб1.ТекСпидометр > ЕСТЬNULL(ПоказанияСпидометра.Спидометр, 0)
ТОГДА Таб1.ТекСпидометр - ЕСТЬNULL(ПоказанияСпидометра.Спидометр, 0)
ИНАЧЕ Таб1.ТекСпидометр
КОНЕЦ КАК Пробег
ИЗ
Таб1 КАК Таб1
ЛЕВОЕ СОЕДИНЕНИЕ РегистрСведений.ПоказанияСпидометра КАК ПоказанияСпидометра
ПО Таб1.Авто = ПоказанияСпидометра.Авто
И Таб1.ПредПериод = ПоказанияСпидометра.Период
УПОРЯДОЧИТЬ ПО
ТекПериод
ВЫБРАТЬ
ПоказанияСпидометра.Авто,
ПоказанияСпидометра.Период КАК ТекПериод,
ПоказанияСпидометра.Пробег КАК ТекСпидометр,
МАКСИМУМ(ПоказанияСпидометраПредыдущие.Период) КАК ПредПериод
ПОМЕСТИТЬ Таб1
ИЗ
РегистрСведений.ПоказанияСпидометра КАК ПоказанияСпидометра
ЛЕВОЕ СОЕДИНЕНИЕ РегистрСведений.ПоказанияСпидометра КАК ПоказанияСпидометраПредыдущие
ПО ПоказанияСпидометра.Период > ПоказанияСпидометраПредыдущие.Период
И ПоказанияСпидометра.Авто = ПоказанияСпидометраПредыдущие.Авто
ГДЕ
ПоказанияСпидометра.Период МЕЖДУ &НачалоПериода И &КонецПериода
И ПоказанияСпидометра.Авто = &Авто
СГРУППИРОВАТЬ ПО
ПоказанияСпидометра.Период,
ПоказанияСпидометра.Авто,
ПоказанияСпидометра.Пробег
;
////////////////////////////////////////////////////////////////////////////////
ВЫБРАТЬ
Таб1.Авто,
Таб1.ТекПериод КАК ТекПериод,
Таб1.ТекСпидометр,
ЕСТЬNULL(ПоказанияСпидометра.Пробег, 0) КАК ПредСпидометр,
ВЫБОР
КОГДА Таб1.ТекСпидометр > ЕСТЬNULL(ПоказанияСпидометра.Пробег, 0)
ТОГДА Таб1.ТекСпидометр - ЕСТЬNULL(ПоказанияСпидометра.Пробег, 0)
ИНАЧЕ Таб1.ТекСпидометр
КОНЕЦ КАК Пробег
ИЗ
Таб1 КАК Таб1
ЛЕВОЕ СОЕДИНЕНИЕ РегистрСведений.ПоказанияСпидометра КАК ПоказанияСпидометра
ПО Таб1.Авто = ПоказанияСпидометра.Авто
И Таб1.ПредПериод = ПоказанияСпидометра.Период
УПОРЯДОЧИТЬ ПО
ТекПериод
ВЫБРАТЬ
ПоказанияСпидометра.Авто,
ПоказанияСпидометра.Период КАК ТекПериод,
ПоказанияСпидометра.Спидометр КАК ТекСпидометр,
МАКСИМУМ(ПоказанияСпидометраПредыдущие.Период) КАК ПредПериод
ПОМЕСТИТЬ Таб1
ИЗ
РегистрСведений.ПоказанияСпидометра КАК ПоказанияСпидометра
ЛЕВОЕ СОЕДИНЕНИЕ РегистрСведений.ПоказанияСпидометра КАК ПоказанияСпидометраПредыдущие
ПО ПоказанияСпидометра.Период > ПоказанияСпидометраПредыдущие.Период
И ПоказанияСпидометра.Авто = ПоказанияСпидометраПредыдущие.Авто
ГДЕ
ПоказанияСпидометра.Период МЕЖДУ НАЧАЛОПЕРИОДА(&НачалоПериода, ДЕНЬ) И КОНЕЦПЕРИОДА(&КонецПериода, ДЕНЬ)
И ПоказанияСпидометра.Авто В(&СписокАвтомоиблей)
СГРУППИРОВАТЬ ПО
ПоказанияСпидометра.Период,
ПоказанияСпидометра.Авто,
ПоказанияСпидометра.Спидометр
;
////////////////////////////////////////////////////////////////////////////////
ВЫБРАТЬ
Таб1.Авто КАК Авто,
Таб1.ТекПериод КАК ТекПериод,
Таб1.ТекСпидометр КАК ТекСпидометр,
ЕСТЬNULL(ПоказанияСпидометра.Спидометр, 0) КАК ПредСпидометр,
ВЫБОР
КОГДА Таб1.ТекСпидометр > ЕСТЬNULL(ПоказанияСпидометра.Спидометр, 0)
ТОГДА Таб1.ТекСпидометр - ЕСТЬNULL(ПоказанияСпидометра.Спидометр, 0)
ИНАЧЕ Таб1.ТекСпидометр
КОНЕЦ КАК Пробег
ИЗ
Таб1 КАК Таб1
ЛЕВОЕ СОЕДИНЕНИЕ РегистрСведений.ПоказанияСпидометра КАК ПоказанияСпидометра
ПО Таб1.Авто = ПоказанияСпидометра.Авто
И Таб1.ПредПериод = ПоказанияСпидометра.Период
УПОРЯДОЧИТЬ ПО
ТекПериод
ИТОГИ
СУММА(Пробег)
ПО
Авто
Украинский 1С форум: всё про 1С 8.3, 1С 8.2, 1С 8.1, 1С 8.0, 1С 7.7
https://pro1c.org.ua