Подсчет кол-ва записей в произвольном запросе

Запросы, планы, оптимизация запросов, ...

Модераторы: kdv, CyberMax

Ответить
pal
Сообщения: 6
Зарегистрирован: 08 фев 2006, 14:51

Подсчет кол-ва записей в произвольном запросе

Сообщение pal » 08 фев 2006, 15:18

Добрый, всем!
Озадачила мою голову проблема: "Как подсчитать кол-во записей возвращаемых произвольным запросом в Firebird?".

Для простых запросов наверное самое простое решение это заменить все что стоит между словами select и from на фразу count(*). Но как быть для запросов с union или group by. Подобная проблема например в Oracle решится тоже быстро, по средством вставки произвольного запроса после слова from. Например select count(*) from (select.....). Но к моему сожалению Firebird не поддерживает такой синтаксис. Понятно что вместо внутреннего select можно сделать вызов ХП в которую в качестве параметра засунуть этот SQL. Но тогда мне (скорее по нехватке знаний о ХП) не совсем ясно как уже внутри этой процедуры либо профетчить все эти записи, либо каким-либо другим способом вытащить кол-во записей.

Может кто-нить предложит вариант решения этой проблемы под Firebird (версия 1.5.2) с использованием либо SQL либо ХП.

Спасибо.

SAMZ
Сообщения: 128
Зарегистрирован: 21 мар 2005, 08:17

Re: Подсчет кол-ва записей в произвольном запросе

Сообщение SAMZ » 08 фев 2006, 16:01

pal писал(а):Добрый, всем!
Озадачила мою голову проблема: "Как подсчитать кол-во записей возвращаемых произвольным запросом в Firebird?".


Может кто-нить предложит вариант решения этой проблемы под Firebird (версия 1.5.2) с использованием либо SQL либо ХП.

Спасибо.
Если запихнешь сколь угодно сложный запрос в ХП и далее
select count(*) from ХП
то получишь искомое к-во без проблем. Ну, а select from select, жди FB2

pal
Сообщения: 6
Зарегистрирован: 08 фев 2006, 14:51

Сообщение pal » 08 фев 2006, 16:23

Если запихнешь сколь угодно сложный запрос в ХП и далее
select count(*) from ХП
то получишь искомое к-во без проблем.
В этом и сотоит один из вопросов.
Внутри ХП я пробовал писать что-то типа

Код: Выделить всё

for execute statement sql_in
do 
 suspend;
end
на что получал сообщение о некорректном синтаксисе. От меня требуют ключевого слова into. Но я не знаю какие параметры могут быть внутри запроса, а потому не могу указать ни какую переменную. Как динамически объявить курсор и запустить по нему fetch я тоже не нашел в описании.

Merlin
Динозавр IB/FB
Сообщения: 1502
Зарегистрирован: 27 окт 2004, 11:44

Re: Подсчет кол-ва записей в произвольном запросе

Сообщение Merlin » 08 фев 2006, 16:29

pal писал(а):Добрый, всем!
Озадачила мою голову проблема: "Как подсчитать кол-во записей возвращаемых произвольным запросом в Firebird?".
В read_commited - единственное 100% решение - пересчитать, загибая пальцы. То есть отфетчить целиком и посмотреть сколько получилось. В снапшоте count даст точную оценку. Но и то и другое - не записей в базе, отвечающих условиям запроса, а записей, видимых транзкции (снапшот) или записей, видимых транзакции + увиденных запросом в процессе фетча, как там у него карта ляжет. Отсюда следует, что стремление знать сие волшебное число на самом деле малоосмысленно. Посему утруждать свою больную голову размышлизмами на тему а как там с юнионами и т.п. мне элементарно лень, фигнёй занимайся самостоятельно :)

pal
Сообщения: 6
Зарегистрирован: 08 фев 2006, 14:51

Re: Подсчет кол-ва записей в произвольном запросе

Сообщение pal » 08 фев 2006, 16:44

Merlin писал(а): ...и то и другое - не записей в базе, отвечающих условиям запроса, а записей, видимых транзкции (снапшот) или записей, видимых транзакции + увиденных запросом в процессе фетча, как там у него карта ляжет.
это я прекрасно понимаю и осознаю. В моем случае система использующая эту фичу будет больше напоминать OLAP а не OLTP систему, а потому количество записей в варианте read_commited и по snapshot буду одинаковые, с достаточно большой вероятностью.

У меня остался один вопрос. Как в ХП мне сделать fetch по всем записям в моем случае. Буду благодарен либо за небольшой кусочек кода (а большим он и не может быть), либо за ссылку на документ в котором это может быть описано.

Merlin
Динозавр IB/FB
Сообщения: 1502
Зарегистрирован: 27 окт 2004, 11:44

Re: Подсчет кол-ва записей в произвольном запросе

Сообщение Merlin » 08 фев 2006, 18:47

pal писал(а): У меня остался один вопрос. Как в ХП мне сделать fetch по всем записям в моем случае.
В ХП - никак. В ней можно запрос (который в процедуре выглядит как цикл For Select) тупо выполнить два раза - сначала сосчитав количество в теле цикла, второй раз выдавая результаты через suspend. Практически то же самое - оформить запрос как view и сделать select count из этого view. Тока не спрашивай меня почему всё это так медленно работает :) Всё-тки кажется, что ты где-то с ветряными мельницами бьёшся, но тебе жить... :)

pal
Сообщения: 6
Зарегистрирован: 08 фев 2006, 14:51

Re: Подсчет кол-ва записей в произвольном запросе

Сообщение pal » 08 фев 2006, 19:01

Merlin писал(а):
В ХП - никак. В ней можно запрос (который в процедуре выглядит как цикл For Select) тупо выполнить два раза - сначала сосчитав количество в теле цикла, второй раз выдавая результаты через suspend.
Проблема только в том что for select требует операнд into в котором я должен указать ровно столько переменных и тех типов которые идут в запросе. А я их не знаю.
Merlin писал(а): Практически то же самое - оформить запрос как view и сделать select count из этого view.
По поводу view я тоже уже думал, но там те же грабли. Для того чтобы его создать мне надо знать по-крайней мере кол-во вытаскиваемых полей. А для этого надо парсить исходный запрос. Чего делать не хочется.

Merlin
Динозавр IB/FB
Сообщения: 1502
Зарегистрирован: 27 окт 2004, 11:44

Сообщение Merlin » 08 фев 2006, 19:10

А. Строим очередной Обобщённый Решатель Задач с Речевым Вводом-Выводом. Эт без меня, сорри.

Ответить