Имя: Пароль:
1C
1С v8
Проблема с запросом, два внутренних соединения
,
0 LLIaMaH
 
08.04.15
06:22
Простенькая конфа по учету показания счетчиков. Пакетным запросом выбираю показания за текущий месяц и за предидущий. Потом в запросе делаю внутреннее соединение с этими двумя таблицами, необходиом получить в выборке только те счетчики по которым есть показания либо в текущем периоде либо в прошлом периоде. Есть два счетчика которые не имеют показаний в прошлом периоде, по какото причине они не попадают в выборку, видимо чето я не догоню в работе механизма соединений таблиц, особенно когда их последовательно два. Если пробовать с каждой ВТ соединять по отдельности то все отрабатывает как положено.

ВЫБРАТЬ
    ПоказанияСчетчиков.Счетчик.Ссылка как Счетчик,
    ПоказанияСчетчиков.Показание
ПОМЕСТИТЬ ПоказанияПрошлогоПериода
ИЗ
    РегистрСведений.ПоказанияСчетчиков КАК ПоказанияСчетчиков
ГДЕ
    ПоказанияСчетчиков.Период = &ДатаОстатков1
;

////////////////////////////////////////////////////////////////////////////////
ВЫБРАТЬ
    ПоказанияСчетчиков.Счетчик.Ссылка как Счетчик,
    ПоказанияСчетчиков.Показание
ПОМЕСТИТЬ ПоказанияТекущегоПериода
ИЗ
    РегистрСведений.ПоказанияСчетчиков КАК ПоказанияСчетчиков
ГДЕ
    ПоказанияСчетчиков.Период = &ДатаОстатков
;

////////////////////////////////////////////////////////////////////////////////
ВЫБРАТЬ    
    Счетчики.Ссылка КАК Счетчик,
    ПоказанияПрошлогоПериода.Показание КАК ПоказаниеПрошлогоПериода,
    ПоказанияТекущегоПериода.Показание КАК ПоказаниеТекущегоПериода
ИЗ
    Справочник.Счетчики КАК Счетчики
         внутреннее СОЕДИНЕНИЕ ПоказанияТекущегоПериода КАК ПоказанияТекущегоПериода
        ПО Счетчики.Ссылка = ПоказанияТекущегоПериода.Счетчик
         внутреннее СОЕДИНЕНИЕ ПоказанияПрошлогоПериода КАК ПоказанияПрошлогоПериода
        ПО Счетчики.Ссылка = ПоказанияПрошлогоПериода.Счетчик
1 LLIaMaH
 
08.04.15
06:25
А вот выборка с временными таблицам, видно что в одной есть счетчики СЭТ4-1/2 №019162 СЭТ4-1/2 №019164    которые по какото причине не попадают в итоговую выборку.

    
Временная таблица: ПоказанияПрошлогоПериода (Записей в результате: 6)    
Счетчик    Показание
Меркурий 230 №13107265    300
СЕ 303  №812023087    100
ЦЭ 68038 № ...    200
Нева 303 1SO  №682810    985
Меркурий 230 №03920533    500
Нева 301 1SO  №012586    5 000
        
Временная таблица: ПоказанияТекущегоПериода (Записей в результате: 8)    
Счетчик    Показание
Меркурий 230 №13107265    600
СЕ 303  №812023087    990
ЦЭ 68038 № ...    1 000
СЭТ4-1/2 №019162    800
СЭТ4-1/2 №019164    700
Нева 303 1SO  №682810    1 500
Меркурий 230 №03920533    1 000
Нева 301 1SO  №012586    8 000
        
Запрос: Справочник.Счетчики (Записей в результате: 6)        
Счетчик    ПоказаниеПрошлогоПериода    ПоказаниеТекущегоПериода
Меркурий 230 №13107265    300    600
СЕ 303  №812023087    100    990
ЦЭ 68038 № ...    200    1 000
Нева 303 1SO  №682810    985    1 500
Меркурий 230 №03920533    500    1 000
Нева 301 1SO  №012586    5 000    8 000
2 SeraFim
 
08.04.15
06:31
внутреннее соединение - это когда записи, удовлетворяющие условию есть в обеих таблицах.
Тебе нужно ЛЕВОЕ соединение и условие, что есть показания либо в текущем периоде либо в прошлом периоде.
3 Dilgorp
 
08.04.15
06:32
(0) по твоему запросу должны попадать только счетчики, которые есть во всех трех таблицах одновременно, не знаю насколько правильно и быстро, но должно сработать:

ВЫБРАТЬ    
    Счетчики.Ссылка КАК Счетчик,
    ПоказанияПрошлогоПериода.Показание КАК ПоказаниеПрошлогоПериода,
    ПоказанияТекущегоПериода.Показание КАК ПоказаниеТекущегоПериода
ИЗ
    Справочник.Счетчики КАК Счетчики
         ЛЕВОЕ СОЕДИНЕНИЕ ПоказанияТекущегоПериода КАК ПоказанияТекущегоПериода
        ПО Счетчики.Ссылка = ПоказанияТекущегоПериода.Счетчик
         ЛЕВОЕ СОЕДИНЕНИЕ ПоказанияПрошлогоПериода КАК ПоказанияПрошлогоПериода
        ПО Счетчики.Ссылка = ПоказанияПрошлогоПериода.Счетчик
ГДЕ
НЕ (ПоказанияПрошлогоПериода.Показание IS NULL И ПоказанияТекущегоПериода.Показание IS NULL)
4 LLIaMaH
 
08.04.15
06:51
Во как. Я думал что внетренее соединение работает только для двух таблиц, и в итоговую выборку попадают все записи из таблиц каждого соединения. Левое соединение не подходит, тогда попадет весь справочник счетчиков, а использовать где наверно не оптимально, хотя я вот выриант накидал не то чтобы он был более оптимален, вроде работает как нада.

ВЫБРАТЬ
    ПоказанияСчетчиков.Счетчик.Ссылка КАК Счетчик,
    ПоказанияСчетчиков.Показание
ПОМЕСТИТЬ ПоказанияПрошлогоПериода
ИЗ
    РегистрСведений.ПоказанияСчетчиков КАК ПоказанияСчетчиков
ГДЕ
    ПоказанияСчетчиков.Период = &ДатаОстатков1
;

////////////////////////////////////////////////////////////////////////////////
ВЫБРАТЬ
    ПоказанияСчетчиков.Счетчик.Ссылка КАК Счетчик,
    ПоказанияСчетчиков.Показание
ПОМЕСТИТЬ ПоказанияТекущегоПериода
ИЗ
    РегистрСведений.ПоказанияСчетчиков КАК ПоказанияСчетчиков
ГДЕ
    ПоказанияСчетчиков.Период = &ДатаОстатков
;

////////////////////////////////////////////////////////////////////////////////
ВЫБРАТЬ
    Счетчики.Ссылка КАК Счетчик,
    ПоказанияПрошлогоПериода.Показание КАК ПоказаниеПрошлогоПериода,
    0 КАК ПоказанияТекущегоПериода
ПОМЕСТИТЬ Общая
ИЗ
    Справочник.Счетчики КАК Счетчики
        ВНУТРЕННЕЕ СОЕДИНЕНИЕ ПоказанияПрошлогоПериода КАК ПоказанияПрошлогоПериода
        ПО Счетчики.Ссылка = ПоказанияПрошлогоПериода.Счетчик

ОБЪЕДИНИТЬ ВСЕ

ВЫБРАТЬ
    Счетчики.Ссылка,
    0,
    ПоказанияТекущегоПериода.Показание
ИЗ
    Справочник.Счетчики КАК Счетчики
        ВНУТРЕННЕЕ СОЕДИНЕНИЕ ПоказанияТекущегоПериода КАК ПоказанияТекущегоПериода
        ПО Счетчики.Ссылка = ПоказанияТекущегоПериода.Счетчик
;

////////////////////////////////////////////////////////////////////////////////
ВЫБРАТЬ
    Общая.Счетчик,
    СУММА(Общая.ПоказаниеПрошлогоПериода) КАК ПоказаниеПрошлогоПериода,
    СУММА(Общая.ПоказанияТекущегоПериода) КАК ПоказанияТекущегоПериода
ИЗ
    Общая КАК Общая

СГРУППИРОВАТЬ ПО
    Общая.Счетчик
5 LLIaMaH
 
08.04.15
06:58
+4 хотя на кой в этом случае было делать ВТ по регистрам отдельно, так прикольней

////////////////////////////////////////////////////////////////////////////////
ВЫБРАТЬ
    Счетчики.Ссылка КАК Счетчик,
    ПоказанияПрошлогоПериода.Показание КАК ПоказаниеПрошлогоПериода,
    0 КАК ПоказанияТекущегоПериода
ПОМЕСТИТЬ Общая
ИЗ
    Справочник.Счетчики КАК Счетчики
        ВНУТРЕННЕЕ СОЕДИНЕНИЕ РегистрСведений.ПоказанияСчетчиков КАК ПоказанияПрошлогоПериода
        ПО Счетчики.Ссылка = ПоказанияПрошлогоПериода.Счетчик
ГДЕ
    ПоказанияПрошлогоПериода.Период = &ДатаОстатков1        

ОБЪЕДИНИТЬ ВСЕ

ВЫБРАТЬ
    Счетчики.Ссылка,
    0,
    ПоказанияТекущегоПериода.Показание
ИЗ
    Справочник.Счетчики КАК Счетчики
        ВНУТРЕННЕЕ СОЕДИНЕНИЕ РегистрСведений.ПоказанияСчетчиков КАК ПоказанияТекущегоПериода
        ПО Счетчики.Ссылка = ПоказанияТекущегоПериода.Счетчик
ГДЕ
    ПоказанияТекущегоПериода.Период = &ДатаОстатков
        
;

////////////////////////////////////////////////////////////////////////////////
ВЫБРАТЬ
    Общая.Счетчик,
    СУММА(Общая.ПоказаниеПрошлогоПериода) КАК ПоказаниеПрошлогоПериода,
    СУММА(Общая.ПоказанияТекущегоПериода) КАК ПоказанияТекущегоПериода
ИЗ
    Общая КАК Общая

СГРУППИРОВАТЬ ПО
    Общая.Счетчик
6 Dilgorp
 
08.04.15
07:00
(4) не проще ли тогда так:
ВЫБРАТЬ
    ПоказанияСчетчиков.Счетчик КАК Счетчик,
    0 КАК ПоказаниеПрошлогоПериода,
    ПоказанияСчетчиков.Показание КАК ПоказаниеТекущегоПериода

ИЗ
    РегистрСведений.ПоказанияСчетчиков КАК ПоказанияСчетчиков
ГДЕ
    ПоказанияСчетчиков.Период = &ДатаОстатков1

ОБЪЕДИНИТЬ ВСЕ

ВЫБРАТЬ
    ПоказанияСчетчиков.Счетчик,
    ПоказанияСчетчиков.Показание,
    0

ИЗ
    РегистрСведений.ПоказанияСчетчиков КАК ПоказанияСчетчиков
ГДЕ
    ПоказанияСчетчиков.Период = &ДатаОстатков
7 Dilgorp
 
08.04.15
07:00
(6) + без ВТ и всего прочего
8 Dilgorp
 
08.04.15
07:02
(5) зачем соединение со справочником?
9 LLIaMaH
 
08.04.15
07:13
(8) Начитался статей и книжек по запросам. Выборку с ОБЪЕДИНИТЬ все равно нада оборачивать во вложенный запрос или выносить во временную таблицу, чтобы потом сгруппировать по Счетчику, вроде как пишут что в свете новых использовать вложенные запросы не феншуйно.

Про соединение со счетчиком, запрос я привел в сокращенном варианте, в полном еще отдельно получаются реквизиты справочника Счетчик и группируются по ним, начитавшись все техже книжек про оптимизацию запросов для СКУля, старался писать оптимально, потому что так или иначе в дальнешем скуль всеравно сделает это соединение, на скока оптимально ХЗ. ну и вроде как через несколько точек вытягивать реквизиты тоже неправильно.
10 Dilgorp
 
08.04.15
07:16
(9) спасибо за информацию)))
11 Simod
 
08.04.15
07:43
ВЫБРАТЬ
    1 КАК Счетчик,
    10 КАК Показание
ПОМЕСТИТЬ ПрошлыйМесяц

ОБЪЕДИНИТЬ ВСЕ

ВЫБРАТЬ
    2,
    20

ОБЪЕДИНИТЬ ВСЕ

ВЫБРАТЬ
    1,
    NULL
;

////////////////////////////////////////////////////////////////////////////////
ВЫБРАТЬ
    2 КАК Счетчик,
    10 КАК Показание
ПОМЕСТИТЬ ТекущийМесяц

ОБЪЕДИНИТЬ ВСЕ

ВЫБРАТЬ
    2,
    20

ОБЪЕДИНИТЬ ВСЕ

ВЫБРАТЬ
    2,
    NULL
;

////////////////////////////////////////////////////////////////////////////////
ВЫБРАТЬ
    ПрошлыйМесяц.Счетчик,
    ПрошлыйМесяц.Показание,
    ТекущийМесяц.Счетчик КАК Счетчик1,
    ТекущийМесяц.Показание КАК Показание1
ИЗ
    ПрошлыйМесяц КАК ПрошлыйМесяц
        ЛЕВОЕ СОЕДИНЕНИЕ ТекущийМесяц КАК ТекущийМесяц
        ПО ПрошлыйМесяц.Счетчик = ТекущийМесяц.Счетчик
ГДЕ
    (НЕ ПрошлыйМесяц.Показание ЕСТЬ NULL
            ИЛИ НЕ ТекущийМесяц.Показание ЕСТЬ NULL )
12 D_E_S_131
 
08.04.15
09:57
(9) "что в свете новых использовать вложенные запросы не феншуйно" — это Вы просто книжки с помощью скорочтения по диагонали читаете.
13 LLIaMaH
 
08.04.15
13:31
(12) А ВЫ вдумчево и сверху вниз? Почему бы сразу не аргументирова толком, без словесного поноса :) Это скорее собирательное мое мнение из разных источников, ну и по логике я так считаю, что если можно вынести вложеный запрос во временную таблицу, хотябы ради улучшения восприятия текста и упрощения отладки, то почему бы это не сделать.
Есть два вида языков, одни постоянно ругают, а вторыми никто не пользуется.