powered by simpleCommunicator - 2.0.61     © 2026 Programmizd 02
Целевая тема:
Создать новую тему:
Автор:
Закрыть
Цитировать
Форумы / Microsoft Access [игнор отключен] [закрыт для гостей] / А почему запрос UNION работает в 3 раза медленнее?
12 сообщений из 12, страница 1 из 1
А почему запрос UNION работает в 3 раза медленнее?
    #32417829
Andrik
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
По совету на этом форуме объеденил запросом две таблицы Товар-Услуга и вижу что эта конструкция работает в 3 раза медленне чем если искать раздельно в обоих таблицах.
Код объеденяющего запроса:
SELECT КодФирмы, КодТовара, 0 as КодУслуги, 'Товар' as Вид, ТипТовара as Тип, ПодтипТовара as Подтип, ИмяТовара as Наименование, ФирмаПроизв, МаркаТовара as Марка, ЦенаОпт, ЦенаРозн, Валюта, ЕдИзмерения
FROM Запр_Товар
UNION
SELECT КодФирмы, 0 as КодТовара, КодУслуги as Код, 'Услуга' as Вид, ТипУслуги as Тип, ПодтипУслуги as Подтип, ИмяУслуги as Наименование, "" as ФирмаПроизв, МаркаУслуги as Марка, "" as ЦенаОпт, Цена as ЦенаРозн, Валюта, ЕдИзмерения
FROM Запр_Услуга
ORDER BY Вид, Наименование;
далее
set rs = db.OpenRecordset("select * from Запр_ТоварУслуга where КодФирмы=5")
это работает примерно в 3 раза медленее чем код:
set rs = db.OpenRecordset("select * from ЗапрТовар where КодФирмы=5")
set rs = db.OpenRecordset("select * from ЗапрУслуга where КодФирмы=5")
Что можно сделать для оптимизации? Чем больше записей тем больше тормозит. Может я что не так делаю?
...
Рейтинг: 0 / 0
А почему запрос UNION работает в 3 раза медленнее?
    #32417830
Andrik
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
КодУслуги as Код слючайно забралось, ничего не изменилось
...
Рейтинг: 0 / 0
А почему запрос UNION работает в 3 раза медленнее?
    #32417849
Фотография Geo
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Делаешь ты все так, только, наверное, у тебя по полю "КодФирмы" обеих таблиц налажена связь с таблицей "Фирмы", и, соответственно, по этим полям построены индексы. Поэтому по индексу поиск происходит быстро. А в Union'е в лучшем случае происходит тот же поиск по всем индексам, входящим в состав исходных таблиц...
...
Рейтинг: 0 / 0
А почему запрос UNION работает в 3 раза медленнее?
    #32417852
Andrik
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
Принцип понятен, но что делать, к запросу ведь индекс не подключишь. Я попробовал без where но эффект примерно тотже (примерно в 2 раза) может есть более элегантный способ?
...
Рейтинг: 0 / 0
А почему запрос UNION работает в 3 раза медленнее?
    #32417857
Фотография Geo
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
> к запросу ведь индекс не подключишь
А почему?

Так, наверное, индексу придется работать:

SELECT * FROM Запр_Товар where КодФирмы=[Параметр]
UNION
SELECT * FROM Запр_Услуга where КодФирмы=[Параметр];

Кроме того, в твоем запрос используется сортировка по наименованию, непонятно зачем нужная, если тебе хочется выбирать записи по другому полю.
...
Рейтинг: 0 / 0
А почему запрос UNION работает в 3 раза медленнее?
    #32417862
Andrik
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
Если я пишу:
SELECT * FROM Запр_Товар union select * from Запр_Услуга
то получаю
"В таблицах или запросах, выбранных в запросе на объединение, не совпадает число столбцов. (Ошибка 3307)"
Про указание WHERE в условиях UNION спасибо я так и сделаю но тогда использовать уже созданный запрос не получиться.
Я уже писал что без WHERE эффект примерно тотже как это ускорить?
set rs = db.OpenRecordset("select * from Запр_ТоварУслуга")
...
Рейтинг: 0 / 0
А почему запрос UNION работает в 3 раза медленнее?
    #32417865
Andrik
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
> Кроме того, в твоем запрос используется сортировка по наименованию, непонятно зачем нужная, если тебе хочется выбирать записи по другому полю.

Дык я выбираю товары по фирме, а на экран эти товары надо по именам и в начале товары а затем услуги вот и получается
ORDER BY Вид, Наименование;
...
Рейтинг: 0 / 0
А почему запрос UNION работает в 3 раза медленнее?
    #32417870
Фотография Geo
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
> В таблицах или запросах, выбранных в запросе на объединение, не совпадает число столбцов

Звездочку я нарисовал только потому, что мне лениво было переписывать имена столбцов - конечно, они нужны. Я имел в виду, что where надо использовать до сортировки.
select ... where ...
union all
select ... where ...
order by ...

> но тогда использовать уже созданный запрос не получиться
Почему тебе нельзя написать

select blablabla where (field1=[param1] or [param1] is null) and (field2=param2 or param2 is null) and ...

, где в качестве параметров могут выступать, скажем, функции?
...
Рейтинг: 0 / 0
А почему запрос UNION работает в 3 раза медленнее?
    #32417874
Andrik
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
Я новичёк и такого не знаю, если не сложно напиши примерчик
...
Рейтинг: 0 / 0
А почему запрос UNION работает в 3 раза медленнее?
    #32417901
Фотография Geo
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
SELECT КодФирмы, КодТовара, 0 as КодУслуги, 'Товар' as Вид, ТипТовара as Тип, ПодтипТовара as Подтип, ИмяТовара as Наименование, ФирмаПроизв, МаркаТовара as Марка, ЦенаОпт, ЦенаРозн, Валюта, ЕдИзмерения from Запр_Товар where (КодФирмы=ДайКодФирмы() or ДайКодФирмы() is null) And (ТипТовара=ДайТипТовара() or ДайТипТовара() is null)
UNION all
SELECT КодФирмы, 0 as КодТовара, КодУслуги as Код, 'Услуга' as Вид, ТипУслуги as Тип, ПодтипУслуги as Подтип, ИмяУслуги as Наименование, "" as ФирмаПроизв, МаркаУслуги as Марка, "" as ЦенаОпт, Цена as ЦенаРозн, Валюта, ЕдИзмерения
FROM Запр_Услуга where (КодФирмы=ДайКодФирмы() or ДайКодФирмы() is null) And (ТипТовара=ДайТипТовара() or ДайТипТовара() is null)
ORDER BY Вид, Наименование;

Выделенное жирным "all" может уберечь тебя от возможных проблем в аналогичных случаях - почитай хелп (по умолчанию одинаковые записи объединяются а во всяких "оборотках" это чревато последствиями).

ДайКодФирмы() и ДайКодТовара() надо описать в каком-нибудь модуле:
Код: plaintext
1.
2.
3.
4.
5.
6.
7.
8.
9.
10.
dim CodeFirm
dim CodeGood

public function ДайКодФирмы()
  ДайКодФирмы=CodeFirm
end sub

public function ДайКодТовара()
  ДайКодТовара=CodeGood
end sub


После этого, перед выполнением запроса ты можешь написать
CodeGood=Null
CodeFirm=null
, тогда запрос вернет все товары и услуги всех фирм и товаров,
или
CodeGood=1
CodeFirm=1
, тогда запрос вернет результат по фирме с кодом 1 и товару с кодом 1.
И т.п.
...
Рейтинг: 0 / 0
А почему запрос UNION работает в 3 раза медленнее?
    #32417971
Фотография AlexJuice
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Кстати, ИМХО отсутствие ALL и дает замедление. Например, в M$ SQL в случае отсутствия ALL записи дополнительно считываются во временную таблицу. Что там делает Акс, не знаю, но что-то подобное
...
Рейтинг: 0 / 0
А почему запрос UNION работает в 3 раза медленнее?
    #32418027
Andrik
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
Спасибо огромное UNION ALL действительно немного ускорило, а поиск в UNION WHERE так-же помог скорость стала сравнима с выбором по отднльности (на глаз немного медленее но горрраздо быстрее чем была в начале). Но я всё-же остался на простом варианте - скопировав во временную таблицу:
DELETE * FROM Табл_ВрТоварУслуга_
INSERT INTO Табл_ВрТоварУслуга_ (...) SELECT ... FROM Запр_Товар WHERE ...
а затем туда-же добавляю
INSERT INTO Табл_ВрТоварУслуга_ (...) SELECT ...FROM Запр_Услуга WHERE ...
эта конструкция работает всё-же быстрее чем такая-же но с
UNION ALL ... WHERE КодФирмы=GlobalFuncCodeFirm()
Но ещё раз спасибо за содействие, применив все советы я нашёл самое быстрое действие, что было-бы невозможно без внешней помощи.
...
Рейтинг: 0 / 0
12 сообщений из 12, страница 1 из 1
Форумы / Microsoft Access [игнор отключен] [закрыт для гостей] / А почему запрос UNION работает в 3 раза медленнее?
Найденые пользователи ...
Разблокировать пользователей ...
Читали форум (0):
Пользователи онлайн (0):
x
x
Закрыть


Просмотр
0 / 0
Close
Debug Console [Select Text]