case в where Оракл | |
---|---|
boba Автор Сообщений: 6269 Откуда: Медвежьи озера- Дата регистрации: 26.03.2001 |
Запутался в какой-то ерунде.
Есть мной же написанные огромные процедуры, в основном много уровневый запросы Появилась необходимость сделать в них банальный переключатель по содержанию некого поля Добавил еще параметр в процедуры lwy in integer Рулить нужно по полю таблицы acgr docnum есть ли единица в первом символе или ее там нет, или неважно. Простые запросы в эту таблицу типа select count(*) from aggr where trim(substr(docnum,1,1)='1') , ... trim(substr(docnum,1,1)!='1' дают разное число записей, что есть верно Теперь залезаю в процедуры и в существующем where, где есть указанная таблица с алиасом b дописываю and case when lwy=0 then 1 when lwy =1 and trim(substr(b.docnum,1,1))='1' then 1 case lwy =2 and trim(substr(b.docnum,1,1))!='1' then 1 end=1 Тестирую с тремя разными lwy -0,1,2 и получаю совершенно неожиданно одинаковые результаты по сумма , что не есть верно. Заменяю case на банальные and ((lwy=0) or (lwy=1 and trim(substr(b.docnum,1,1))='1') or (lwy =2 and trim(substr(b.docnum,1,1))!='1')) и все верно, суммы для разных lwy разные, но вроде так плохо для оптимизации. Что неверно в случае case не понимаю, вроде это одно и тоже. Самое поганое, не проверив результат уже 12 процедур поменял с case Исправлено 1 раз(а). Последнее : boba, 02.10.21 21:30 |
Re: case в where Оракл | |
---|---|
sphinx Сообщений: 31182 Откуда: Каменск-Уральски Дата регистрации: 22.11.2006 |
Ничего не понял. Может потому, что у меня нет таблиц и процедур.
------------------ "Veni, vidi, vici!"(с) |
Re: case в where Оракл | |
---|---|
boba Автор Сообщений: 6269 Откуда: Медвежьи озера- Дата регистрации: 26.03.2001 |
Но вот есть место в середине процедуры, где в where
уже есть условия на упомянутую таблицу. Добавляю в условие and case .... с параметром lwy =0,1,2 При котором нужно для 0 условие не менять, при lwy=1 и trim(substr(docnum,1,1))!='1' при lwy =2 и trim(substr(docnum,1,1))='1' Добавляю в where указанный case получаю совершенно одинаковые независимо от lwy результаты |
Re: case в where Оракл | |
---|---|
sphinx Сообщений: 31182 Откуда: Каменск-Уральски Дата регистрации: 22.11.2006 |
Может лучше так:
Ведь если ВПЕРЕДИ один пробел - он и у тебя сначала отрежется слева, а потом превратится в пустое значение (после trim). ------------------ "Veni, vidi, vici!"(с) |
Re: case в where Оракл | |
---|---|
boba Автор Сообщений: 6269 Откуда: Медвежьи озера- Дата регистрации: 26.03.2001 |
Завтра на работе проверю, но скорее всего так и написал,
а тут ошибся |
Re: case в where Оракл | |
---|---|
sphinx Сообщений: 31182 Откуда: Каменск-Уральски Дата регистрации: 22.11.2006 |
Цитата:
Здесь CASE всегда вернет 1, а значит от параметра lwy запрос никак не зависит. Обычно проверяют как-то так:
------------------ "Veni, vidi, vici!"(с) Исправлено 3 раз(а). Последнее : sphinx, 03.10.21 08:40 |
Re: case в where Оракл | |
---|---|
boba Автор Сообщений: 6269 Откуда: Медвежьи озера- Дата регистрации: 26.03.2001 |
Ну и как ты такое в where поместишь,
если там возврат то 1 то 2 я же сравниваю весь блок с 1 case end=1 lwy на входе имеет одно из значений 0, 1, 2 Отдали 1, нужно чтобы сработала ветка subtr(trim(numdoc),1,1)='1' при lwy =2 ветка subtr(trim(numdoc),1,1)!='1' поэтому всегда и возвращаю 1 |
Re: case в where Оракл | |
---|---|
sphinx Сообщений: 31182 Откуда: Каменск-Уральски Дата регистрации: 22.11.2006 |
Легко. Кинь оригинальный запрос и тестовые данные.
------------------ "Veni, vidi, vici!"(с) |
Re: case в where Оракл | |
---|---|
boba Автор Сообщений: 6269 Откуда: Медвежьи озера- Дата регистрации: 26.03.2001 |
Это все на работе
Не модифицированный код одной из 25 процедур ниже В него добавлен lwy int integer, Cама упомянутая модификация в этом месте ____________________________________________________ where b.codgr = a.codgr and b.period between per1 and per2 and b.codplan = 3705763001 and case ..... end =1 ( это вставка, про которую говорил) При lwy=1 b lwy =2 результат в цифрах должен отличаться от lwy =0 _________________________________________________________ procedure usrfsd76(per1 in integer, per2 in integer, p_cursor out t_SLRCursor) is begin open p_cursor for select case when f10022 != ' ' then '{' || substr(f10022, 1, 6) || '}' || substr(f10022, 7) else ' ' end as f10022, case when f10023 != ' ' then '{' || substr(f10023, 1, 6) || '}' || substr(f10023, 7) else ' ' end as f10023, F_M0210, F_M0908, F_M0202, F_M0201, F_M0213, F_M0209, F_M0204, lnone from (select * from (select f6004, f10022, f10023, f5100, sum(case when flagcredit = 1 then -smr else smr end) as smr from (select case when ss.nminref = '_КОНСОЛИДАЦИЯ' then ' ' else aa.nminref end as f10022, case when ss.nminref = '_КОНСОЛИДАЦИЯ' then ' ' else bb.nminref end as f10023, cc.nminref as f5100, case when ss.nminref = '_КОНСОЛИДАЦИЯ' then '_КОНСОЛИДАЦИЯ' else 'Не Консолидация' end as f6004, kk.codtr, kk.flagcredit, kk.smr from (select max(f3711317001) as f3711317001, max(f3706422001) as f3706422001, max(f3706983001) as f3706983001, max(f3170404001) as f3170404001, max(f3572367001) as f3572367001, flagcredit, codtr, smr, count(*) from (select decode(f.codref, 3711317001, f.codinref) as f3711317001, decode(f.codref, 3706422001, f.codinref) as f3706422001, decode(f.codref, 3706983001, f.codinref) as f3706983001, decode(f.codref, 3170404001, f.codinref) as f3170404001, decode(f.codref, 3572367001, f.codinref) as f3572367001, flagcredit, codtr, smr from (select c.codref, c.codinref, c.flagcredit, a.codtr, sum(a.summaincur) as smr from acctrans a, acctransgr b, acctransref c where b.codgr = a.codgr and b.period between per1 and per2 and b.codplan = 3705763001 and a.codtr = c.codtr and ((a.accc = 76 and c.flagcredit = 1) or (a.accd = 76 and c.flagcredit = 0)) group by a.codtr, c.flagcredit, c.codref, c.codinref order by a.codtr, c.flagcredit, c.codref, c.codinref) f) where f3711317001 is not null or f3706422001 is not null or f3706983001 is not null or f3170404001 is not null group by codtr, flagcredit, smr order by codtr, flagcredit) kk left outer join refuser aa on aa.codref = 3711317001 and kk.f3711317001 = aa.codinref left outer join refuser bb on bb.codref = 3706422001 and kk.f3706422001 = bb.codinref left outer join refuser cc on cc.codref = 3706983001 and kk.f3706983001 = cc.codinref left outer join (select case when nvl(t.value, '0') = 0 then tt.nminref else '_КОНСОЛИДАЦИЯ' end as nminref, tt.codinref from REFITEMATTR t, refuser tt where t.codref = 3170404001 and codattr = 3715605001 and tt.codref = 3170404001 and tt.codinref = t.codinref) ss on kk.f3170404001 = ss.codinref left outer join refuser ee on ee.codref = 3572367001 and kk.f3572367001 = ee.codinref) group by f6004, f10022, f10023, f5100, flagcredit order by f6004 asc, f10022, f10023, f5100, flagcredit) PIVOT(SUM(smr) for f5100 in('', 'F_M0210 ПРОЧИЕ ОБОРОТЫ' as F_M0210, 'F_M0908 КУРСОВЫЕ РАЗНИЦЫ' as F_M0908, 'F_M0202 РАСЧЕТЫ ДЕНЕЖНЫМИ СРЕДСТВАМИ' as F_M0202, 'F_M0201 РЕАЛИЗАЦИЯ С НДС (КТ 90)' as F_M0201, 'F_M0213 ЗАЧЕТ АВАНСА' as F_M0213, 'F_M0209 КУРСОВАЯ РАЗНИЦА' as F_M0209, 'F_M0204 Взаимозачет задолженности' as F_M0204 , 'NULL НЕ ОПРЕДЕЛЕНО' as lnone )) order by f6004 asc, f10022, f10023); end usrfsd76; |
Re: case в where Оракл | |
---|---|
Simple777 Сообщений: 33855 Дата регистрации: 05.11.2006 |
|
Re: case в where Оракл | |
---|---|
PaulWist Сообщений: 14620 Дата регистрации: 01.04.2004 |
Володь, так выражение
всё равно приведёт к сканированию таблицы, оно ничем не отличается от OR, за исключением когда lwy=0. ------------------ Есть многое на свете, друг Горацио... Что и не снилось нашим мудрецам. (В.Шекспир Гамлет) Исправлено 2 раз(а). Последнее : PaulWist, 03.10.21 22:10 |
Re: case в where Оракл | |
---|---|
sphinx Сообщений: 31182 Откуда: Каменск-Уральски Дата регистрации: 22.11.2006 |
Только на работе. Если воссоздан проблему. Нет там ничего, или ошибка синтаксиса (как показал) или логики. Я не сказал, что уже мне в, е понятно.. Мы все исходим из предположений.
Смогу воссоздать проблему - там будет видно. Удачи, Володя. ------------------ "Veni, vidi, vici!"(с) |
© 2000-2024 Fox Club  |