powered by simpleCommunicator - 2.0.59     © 2025 Programmizd 02
Целевая тема:
Создать новую тему:
Автор:
Закрыть
Цитировать
Форумы / Sybase ASA, ASE, IQ [игнор отключен] [закрыт для гостей] / Оптимизация запросов в ASA7
11 сообщений из 11, страница 1 из 1
Оптимизация запросов в ASA7
    #32690158
Lucky SB
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
Подскажите плиз как оптимизируются запросы в ASA7 ...
Sybase ASA7 7.0.3 (2047)
Сервер P4 - 2.8/1Gb RAM
Есть вот такой запрос (на самом деле полей больше выбирается, но основной упор ИМХО надо сделать на подselect)

Код: plaintext
1.
2.
3.
4.
5.
6.
7.
8.
9.
10.
11.
12.
select spd.ID,
         spd.subscriberID,
         eventSum   = isnull((select sum(Qty) from entry
                                         where accountID=a.ID
                                         and (entryDate between spd.periodStart and spd.PeriodEnd, 1 
                                      )
                                  and entryType >  0 
                              ), 0 ),
     from
          subscriberPeriodData spd,
          Account a
     where spd.subscriberID = a.SubscriberID

В таблице entry около миллиона записей.
Под условия select попадает от 10000 до 25000 записей
Во время выполнения этого запроса загрузка проца поднимается до 100% и сервер перестает отвечать на внешние раздражители...

По таблице entry есть вот такие индексы:

Код: plaintext
1.
2.
3.
4.
5.
6.
7.
8.
ALTER TABLE "DBA"."Entry"                                                       
        ADD FOREIGN KEY "Account" ("AccountID")                                 
        REFERENCES "DBA"."Account" ("ID")                                       

CREATE INDEX "XIF463Entry" ON "DBA"."Entry"                                     
(                                                                               
        "AccountID" ASC                                                         
)                                                                               

Поможет ли, если я создам индекс
Код: plaintext
1.
CREATE INDEX XIF464Entry ON DBA.Entry (AccountID ASC, EntryDate ASC ) 
Или нужен вот такой:
Код: plaintext
1.
CREATE INDEX XIF465Entry ON DBA.Entry (AccountID ASC, EntryDate ASC, entryType)
Может мне полегчает, если в запросе изменить entryType > 0 на
entryType <> 0 или на not entryType = 0 ?
В принципе у entryType всего 3 значения может быть.
И одно из них встречается намного чаще, чем два других (около 98%)

Или тут ничего не поможет и ASA не умеет делать быстрые подсчеты на таблицах в миллион записей ?
...
Рейтинг: 0 / 0
Оптимизация запросов в ASA7
    #32690176
Фотография Рыжий Кот
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
А вот такая инструкция в семерке есть? Это чтобы сервер все-таки ворочался.

Код: plaintext
SET TEMPORARY OPTION BACKGROUND_PRIORITY = ON

...
Рейтинг: 0 / 0
Оптимизация запросов в ASA7
    #32690185
Фотография ASCRUS
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Сколько записей в таблицах "subscriberPeriodData" и "Account", сколько записей в среднем обрабатывает подзапрос на каждую запись главного запроса ?

И еще вопросик - поддерживает ли 7-ая версия подзапросы в секции FROM ?

Код: plaintext
1.
_________________________
работаю, никого не трогаю
...
Рейтинг: 0 / 0
Оптимизация запросов в ASA7
    #32690219
Lucky SB
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
Вот наконец count по entry отработал:
1518441 записей.
ASCRUS
Сколько записей в таблицах "subscriberPeriodData" и "Account", сколько записей в среднем обрабатывает подзапрос на каждую запись главного запроса ?

Код: plaintext
1.
2.
3.
4.
5.
6.
7.
8.
9.
select count () from 
          subscriberPeriodData spd,
          Account a
     where spd.subscriberID = a.SubscriberID
go

 count(*)    
  -----------  
         4906  

Торможения начинаются при попадании в подзапрос около 10000 или более записей.

ASCRUS
И еще вопросик - поддерживает ли 7-ая версия подзапросы в секции FROM ?

Ты вот про это ?
Пример из доки:
Код: plaintext
1.
2.
3.
4.
5.
6.
7.
8.
9.
SELECT lname, fname, number_of_orders
FROM customer JOIN
     ( SELECT cust_id, count(*)
       FROM sales_order
        GROUP BY cust_id )
     AS sales_order_counts ( cust_id,
                             number_of_orders )
ON ( customer.id = sales_order_counts.cust_id )
WHERE number_of_orders >  3 

Рыжий кот
А вот такая инструкция в семерке есть? Это чтобы сервер все-таки ворочался.
SET TEMPORARY OPTION BACKGROUND_PRIORITY = ON


Есть.
Стоит OFF.
Стоит попробовать ON поставить ?
...
Рейтинг: 0 / 0
Оптимизация запросов в ASA7
    #32690290
Фотография ASCRUS
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
1. Сделайте индекс по полям (Account_id, entryDate). Включать в индексы поле entryType смысла нет, раз там так мало значений, то ничего, кроме разбухания размера и страниц индексов добиться нельзя.

2. Ваш запрос на каждую строчку главного запроса сканирует через subquery огромную таблицу. То есть если главный запрос обхватывает 10 000 записей, то именно 10 000 раз будет идти скан таблицы entry. И тут уже без разницы, как осуществлятся сканирование - чтением таблицы или же индекса. В любом случае это будет долгая и затратная операция, так как по такому кол-ву записей СУБД не сможет эту таблицу всю вынести в кэш и постоянно будет заново читать данные с диска. Я рекомендую в раздел запроса "SELECT" включать только подзапросы, в которых участвует таблицы с малым кол-вом записей и с одной стороны для СУБД не критично все записи подзапроса вывести в кэш и вызывать хоть 10 000 раз, с другой стороны это позволяет иногда разрулить сложные части запросов и добиться правильных соединений в запросе с точки зрения оптимизатора ASA, то есть достичь лучшего плана. В Вашем случае однозначно таблица Entry должна быть перенесена в секцию FROM. Если 7-ая версия поддерживает JOIN-синтаксис, то примерно это будет выглядеть так:
Код: plaintext
1.
2.
3.
4.
5.
SELECT spd.ID, spd.subscriberID, eventSum = IsNull(Sum(e.Qty),  0 )
FROM subscriberPeriodData spd
  INNER JOIN Account a ON spd.subscriberID = a.SubscriberID
  LEFT JOIN entry e ON e.accountID=a.ID AND 
                       (e.entryDate BETWEEN spd.periodStart AND spd.PeriodEnd) AND
                       e.entryType >  0 

Если JOIN-ов еще нет, то можно соединить таблицы в стандарте ANSI SQL, т.е. через WHERE, используя для левостороннего соединения оператор "*=" (как точно правильно я не помню, нужно смотреть BOL).


Код: plaintext
1.
_________________________
работаю, никого не трогаю
...
Рейтинг: 0 / 0
Оптимизация запросов в ASA7
    #32690343
Lucky SB
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
ASCRUS
1. Сделайте индекс по полям (Account_id, entryDate). Включать в индексы поле entryType смысла нет, раз там так мало значений, то ничего, кроме разбухания размера и страниц индексов добиться нельзя.


Сделал.
Вроде слегка полегчало.
Насколько я понимаю сервер сам соображает, что надо использовать индекс

автор
2. Ваш запрос на каждую строчку главного запроса сканирует через subquery огромную таблицу. То есть если главный запрос обхватывает 10 000 записей, то именно 10 000 раз будет идти скан таблицы entry.

В любом случае это будет долгая и затратная операция, так как по такому кол-ву записей СУБД не сможет эту таблицу всю вынести в кэш и постоянно будет заново читать данные с диска.
Я рекомендую в раздел запроса "SELECT" включать только подзапросы, в которых участвует таблицы с малым кол-вом записей и с одной стороны для СУБД не критично все записи подзапроса вывести в кэш и вызывать хоть 10 000 раз, с другой стороны это позволяет иногда разрулить сложные части запросов и добиться правильных соединений в запросе с точки зрения оптимизатора ASA, то есть достичь лучшего плана. В Вашем случае однозначно таблица Entry должна быть перенесена в секцию FROM. Если 7-ая версия поддерживает JOIN-синтаксис, то примерно это будет выглядеть так:
SELECT spd.ID, spd.subscriberID, eventSum = IsNull(Sum(e.Qty), 0)
FROM subscriberPeriodData spd
INNER JOIN Account a ON spd.subscriberID = a.SubscriberID
LEFT JOIN entry e ON e.accountID=a.ID AND
(e.entryDate BETWEEN spd.periodStart AND spd.PeriodEnd) AND
e.entryType > 0
Если JOIN-ов еще нет, то можно соединить таблицы в стандарте ANSI SQL, т.е. через WHERE, используя для левостороннего соединения оператор "*=" (как точно правильно я не помню, нужно смотреть BOL).


Главный запрос охватывает от 12 до 30 записей.
И у меня в боевом запросе два подзапроса:
один берет записи с entryType>0, а другой с entryType=0
Т.е должно будет выглядеть примерно так ?

Код: plaintext
1.
2.
3.
4.
5.
6.
7.
8.
9.
10.
11.
SELECT spd.ID, spd.subscriberID, eventSum = IsNull(Sum(e.Qty),  0 ), paymentSum = IsNull(Sum(e1.Qty),  0 )
FROM subscriberPeriodData spd
  INNER JOIN Account a ON spd.subscriberID = a.SubscriberID
  LEFT JOIN entry e ON e.accountID=a.ID AND 
                       (e.entryDate BETWEEN spd.periodStart AND spd.PeriodEnd) AND
                       e.entryType >  0 
  INNER JOIN Account a ON spd.subscriberID = a.SubscriberID
  LEFT JOIN entry e1 ON e1.accountID=a.ID AND 
                       (e1.entryDate BETWEEN spd.periodStart AND spd.PeriodEnd) AND
                       e1.entryType =  0 

...
Рейтинг: 0 / 0
Оптимизация запросов в ASA7
    #32690441
Sergey Orlov
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Я бы посоветовал бы вытащить поле где имется подзапрос во внешнюю процедуру, т.е. нечто
select spd.ID,
spd.subscriberID,
eventSum(a.ID,spd.periodStart,spd.PeriodEnd)
from
subscriberPeriodData spd,
Account a
where spd.subscriberID = a.SubscriberID

functon eventSum(in ID,in periodStart,in PeriodEnd)
return ....
begin
declare a ...;
a = isnull((select sum(Qty) from entry where accountID=ID and (entryDate between spd.periodStart and spd.PeriodEnd),1
) and entryType > 0
.....
end
...
Рейтинг: 0 / 0
Оптимизация запросов в ASA7
    #32690549
Фотография ASCRUS
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
авторСделал.
Вроде слегка полегчало.
Насколько я понимаю сервер сам соображает, что надо использовать индекс
Угу, обязательно должен. Индекс этот для него в самый раз будет.

авторГлавный запрос охватывает от 12 до 30 записей.
И у меня в боевом запросе два подзапроса:
один берет записи с entryType>0, а другой с entryType=0
Т.е должно будет выглядеть примерно так ?

Код: plaintext
1.
2.
3.
4.
5.
6.
7.
8.
9.
10.
11.
SELECT spd.ID, spd.subscriberID, eventSum = IsNull(Sum(e.Qty),  0 ), paymentSum = IsNull(Sum(e1.Qty),  0 )
FROM subscriberPeriodData spd
  INNER JOIN Account a ON spd.subscriberID = a.SubscriberID
  LEFT JOIN entry e ON e.accountID=a.ID AND 
                       (e.entryDate BETWEEN spd.periodStart AND spd.PeriodEnd) AND
                       e.entryType >  0 
  INNER JOIN Account a ON spd.subscriberID = a.SubscriberID
  LEFT JOIN entry e1 ON e1.accountID=a.ID AND 
                       (e1.entryDate BETWEEN spd.periodStart AND spd.PeriodEnd) AND
                       e1.entryType =  0 


Гм - ну зачем же так сложно ? :)
1. Дважды сканировать таблицу с 1,5 миллионом записей явно не стоит, особенно, если можно без этого обойтись.
2. В Вашем запросе "entry e1" можно смело связать с "Account a" и выбросить из связки зачем то дублирующуюся таблицу "Account a" (или это просто опечатка ?)
3. Без GROUP BY работать не будет, у нас же все таки аггрегатный запрос.
3. Раз уж нам надо посчитать 2 суммы, зависящие просто от условия при подсчете, давайте именно так и делать:
Код: plaintext
1.
2.
3.
4.
5.
6.
7.
8.
9.
SELECT
  spd.ID, spd.subscriberID,
  eventSum = IsNull(Sum(IF e.entryType >  0  THEN e.Qty ELSE  0  END IF),  0 ), 
  paymentSum = IsNull(Sum(IF e.entryType =  0  THEN e.Qty ELSE  0  END IF),  0 )
FROM subscriberPeriodData spd
  INNER JOIN Account a ON spd.subscriberID = a.SubscriberID
  LEFT JOIN entry e ON e.accountID=a.ID AND 
                       (e.entryDate BETWEEN spd.periodStart AND spd.PeriodEnd)
GROUP BY spd.ID, spd.subscriberID
Вот тут то все и становиться на свои места - поле entryType используется по назначению, то есть используется при подсчете сумм, а не фильтрации таблицы, таблица entry сканируется всего один раз, условие, входящие в аггрегатную функцию sum будет эффективно выполняться и не сильно тормозить, во всяком случае это будет гораздо быстрее, чем 2 раза сканить таблицу entry (всегда стоит помнить про чтение с диска и размер кэша, но про процессорную мощность тоже забывать не следует, так как иногда легче посчитать, чем просканировать).

Далее если так "чисто случайно" в таблице Entry всегда accountID имеет аналогичную запись в Account (то есть установлен Foreign Key между этими таблицами), то можно вообще вместо LEFT JOIN поставить INNER JOIN, получить чистое прямое соединение, и наслаждаться скоростью запроса :)

Sergey OrlovЯ бы посоветовал бы вытащить поле где имется подзапрос во внешнюю процедуру
А вот этого делать не стоит вообще никогда, кроме случаев, когда функции передается константа или переменная. Сделав такое мы получим:
1. Все равно функция будет вызываться на каждую строчку главного запроса, что ничем не отличается от того же subquery.
2. Функция в отличие даже от subquery никогда не войдет в план запроса, откуда оптимизатору знать, чего там она и как делает. Не стоит забывать, что для функций оптимизатор предполагает, что они служат для вычислений и преобразований, а не в качестве средства получения запроса с 1,5 миллионной таблицы.
3. Функцию еще нужно каждый раз вызвать и выполнить, что тоже дополнительно занимает время и даже ресурсы, так как в функции обьявляются и удаляются сборщиком мусора переменные.
... и еще много много другого, что можно долго перечислять ...

Так что я думаю использовать в запросах функции нужно только тогда, когда они действительно нужны. Даже если можно обойтись средствами WatcomSQL, лучше обойтись ими (тот же IF END IF), чем писать универсальную функцию, все назначение которой - сократить чуть чуть кода при написании скриптов. Сократить то можно, вот только производительность сокращается так же, а это для БД не приемлемо.
...
Рейтинг: 0 / 0
Оптимизация запросов в ASA7
    #32691291
Sergey Orlov
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
авторГлавный запрос охватывает от 12 до 30 записей.
И у меня в боевом запросе два подзапроса:
один берет записи с entryType>0, а другой с entryType=0
Т.е должно будет выглядеть примерно так ?


Sergey OrlovЯ бы посоветовал бы вытащить поле где имется подзапрос во внешнюю процедуру
А вот этого делать не стоит вообще никогда, кроме случаев, когда функции передается константа или переменная. Сделав такое мы получим:
1. Все равно функция будет вызываться на каждую строчку главного запроса, что ничем не отличается от того же subquery.
2. Функция в отличие даже от subquery никогда не войдет в план запроса, откуда оптимизатору знать, чего там она и как делает. Не стоит забывать, что для функций оптимизатор предполагает, что они служат для вычислений и преобразований, а не в качестве средства получения запроса с 1,5 миллионной таблицы.
3. Функцию еще нужно каждый раз вызвать и выполнить, что тоже дополнительно занимает время и даже ресурсы, так как в функции обьявляются и удаляются сборщиком мусора переменные.
... и еще много много другого, что можно долго перечислять ...

Так что я думаю использовать в запросах функции нужно только тогда, когда они действительно нужны. Даже если можно обойтись средствами WatcomSQL, лучше обойтись ими (тот же IF END IF), чем писать универсальную функцию, все назначение которой - сократить чуть чуть кода при написании скриптов. Сократить то можно, вот только производительность сокращается так же, а это для БД не приемлемо.
Но обрати внимание, что в основном запросе данное поле вычисляемое, да в план запроса функция не войдет, но в оптимизировать ее одну легче, и второе основной план запроса 10-30 записей, т.е. вызвать функцию надо всего 10-30 раз
...
Рейтинг: 0 / 0
Оптимизация запросов в ASA7
    #32691678
Фотография ASCRUS
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
авторНо обрати внимание, что в основном запросе данное поле вычисляемое, да в план запроса функция не войдет, но в оптимизировать ее одну легче, и второе основной план запроса 10-30 записей, т.е. вызвать функцию надо всего 10-30 раз
Ну как оказалось не 10-30 раз, а 20-60, так как автор одновременно считает 2 суммы по разным условиям (мой последний вариант запроса делает это один раз). Во вторых есть один ньюанс - без функции мой запрос будет входить в главный план запроса и соотвествующе по плану индекс и таблицы будет последовательно сканироваться один раз, т.е. за один проход. В Вашем случае что функция, что использование Subquery означает сканирование этой довольно таки большой таблицы для каждой записи главного запроса, причем каждый раз с корневой страницы индекса. Еестественно будет медленнее.

P.S. На практике часто оказывается, что с функциями или subquery запросы выполняются быстрее, чем с разворачиванием всего запроса в корневой план (то есть секцию FROM). Но нельзя это воспринимать как аксиому. Дело в том, что если оптимизатор не смог правильно и оптимально связать таблицы в плане, то он может построить не эффективный и тормозной план запроса. В случае же с функциями уже изначально план запроса получается меньше и шансов, что оптимизатор соединит все правильно как в главном, так и запросе функции, соотвествующе больше. Однако это не означает, что применение функций выгодней, чем написание большого запроса. Это только означает, что в запросе нужно переписать соединения таблиц, достроить нужные индексы, обьединить часть мелких таблиц во времянки - в общем добиться оптимального и красивого плана запроса и использование функций и subquery по скорости выполнения, особенно при дальнейшем росте данных окажутся далеко сзади.

Код: plaintext
1.
_________________________
работаю, никого не трогаю
...
Рейтинг: 0 / 0
Оптимизация запросов в ASA7
    #32691983
Lucky SB
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
Огромное спасибо за помощь.
В принципе мой опыт работы с SQL ограничивается MySQL, и в общем-то я первый раз сталкиваюсь с оптимизацией запроса по базам с миллионами записей...
Про запрос с IF я как-то не сообразил ;)
Самая большая проблема - это то, что база-то написана не мной. Я ее пользователь/администратор, вот и приходиться практически наощупь в ней копаться и пытатся оптимизировать.
Вот такой запрос был:
Код: plaintext
1.
2.
3.
4.
5.
6.
7.
8.
9.
10.
11.
12.
13.
14.
15.
16.
17.
18.
19.
20.
21.
22.
23.
24.
25.
26.
27.
28.
29.
30.
31.
32.
33.
34.
35.
36.
37.
38.
39.
40.
41.
42.
43.
44.
45.
46.
47.
48.
49.
50.
51.
52.
53.
54.
55.
56.
57.
58.
59.
60.
61.
62.
63.
   select spd.ID,
          spd.subscriberID,
          s.Name,
          s.FullName,
          s.ContrNumber,
          s.ContrDate,
          s.IsLegal,
          accountID = a.ID,
          accountNumber = a.Number,
          currencyCode = cur.code,
          currencyName = cur.Name,
          spd.periodStart,
          spd.periodEnd,

          fakturaNumber = (select fakturaNumber from accountPeriodData where subscriberPeriodDataId = spd.ID and accountID = a.ID),
          accNumber     = (select accNumber from accountPeriodData where subscriberPeriodDataId = spd.ID and accountID = a.ID),
          accDate       = (select accDate from accountPeriodData where subscriberPeriodDataId = spd.ID and accountID = a.ID),

          s.paymentDate,
          saldoStart = isnull((select saldo from subscriberPeriodData spd2,
                                                 accountPeriodData apd2
                                    where spd2.subscriberID = @subscriberID
                                      and spd2.periodEnd = dateadd(second,- 1 ,spd.periodStart)
                                      and apd2.subscriberPeriodDataID = spd2.ID
                                      and apd2.accountID = a.ID), 0 ),
          eventSum   = isnull((select sum(Qty) from entry


                                where accountID=a.ID
                                  and (entryDate between spd.periodStart and spd.PeriodEnd

                                      , 1 

                                      )
                                  and entryType >  0 
                              ), 0 ),
          paymentSum = isnull((select sum(Qty) from entry


                                where accountID=a.ID
                                  and (entryDate between spd.periodStart and spd.PeriodEnd

                                      , 1 

                                      )
                                  and isnull(entryType, 0 ) =  0 
                              ), 0 ),
          SaldoEnd   = (select saldo from accountPeriodData where subscriberPeriodDataId = spd.ID and accountID = a.ID)

     from Subscriber s,
          subscriberPeriodData spd,
          Account a,
          GroupAccount ga,
          Currency cur
    where s.ID = @SubscriberID
      and spd.subscriberID = s.ID
      and a.SubscriberID   = s.ID
      and a.accType in ( 4 , 5 )  -- Берем только счета с нашими услугами (исключаем услуги провайдеров нам) 
      and not exists (select  1  from account where subscriberID = s.ID and parentID = a.ID and accType in ( 4 , 5 ))  -- Исключаем балансовые счета 
      and ga.ID     = a.ID
      and cur.ID    = ga.CurrencyID

    order by spd.periodStart desc 
А вот такой запрос у меня получился:

Код: plaintext
1.
2.
3.
4.
5.
6.
7.
8.
9.
10.
11.
12.
13.
14.
15.
16.
17.
18.
19.
20.
21.
22.
23.
24.
25.
26.
27.
28.
29.
30.
31.
32.
33.
34.
35.
36.
37.
38.
39.
40.
41.
42.
43.
44.
45.
46.
47.
48.
49.
50.
51.
52.
53.
54.
55.
56.
57.
58.
59.
   select spd.ID,
          spd.subscriberID,
          s.Name,
          s.FullName,
          s.ContrNumber,
          s.ContrDate,
          s.IsLegal,
          accountID = a.ID,
          accountNumber = a.Number,
          currencyCode = cur.code,
          currencyName = cur.Name,
          spd.periodStart,
          spd.periodEnd,
          fakturaNumber = (select fakturaNumber from accountPeriodData where subscriberPeriodDataId = spd.ID and accountID = a.ID),
          accNumber     = (select accNumber from accountPeriodData where subscriberPeriodDataId = spd.ID and accountID = a.ID),
          accDate       = (select accDate from accountPeriodData where subscriberPeriodDataId = spd.ID and accountID = a.ID),
          s.paymentDate,
          saldoStart = isnull((select saldo from subscriberPeriodData spd2,
                                                 accountPeriodData apd2
                                    where spd2.subscriberID = @subscriberID
                                      and spd2.periodEnd = dateadd(second,- 1 ,spd.periodStart)
                                      and apd2.subscriberPeriodDataID = spd2.ID
                                      and apd2.accountID = a.ID), 0 ),
          eventSum = IsNull(Sum(IF e.entryType >  0  THEN e.Qty ELSE  0  END IF),  0 ), 
          paymentSum = IsNull(Sum(IF e.entryType =  0  THEN e.Qty ELSE  0  END IF),  0 ),

          SaldoEnd   = (select saldo from accountPeriodData where subscriberPeriodDataId = spd.ID and accountID = a.ID)

     from Subscriber s
  INNER JOIN subscriberPeriodData spd ON spd.subscriberID = s.ID
  INNER JOIN Account a ON s.ID = a.SubscriberID
  INNER JOIN entry e ON e.accountID=a.ID AND
                       (e.entryDate BETWEEN spd.periodStart AND spd.PeriodEnd)
  INNER JOIN GroupAccount ga ON ga.ID     = a.ID
  INNER JOIN Currency cur ON cur.ID    = ga.CurrencyID
    where s.ID = @SubscriberID
      and a.accType in ( 4 , 5 ) 
      and not exists (select  1  from account where subscriberID = s.ID and parentID = a.ID and accType in ( 4 , 5 )) 
    group by
          spd.ID,
          spd.subscriberID,
          s.Name,
          s.FullName,
          s.ContrNumber,
          s.ContrDate,
          s.IsLegal,
          accountID,
          accountNumber,
          currencyCode,
          currencyName,
          spd.periodStart,
          spd.periodEnd,
          fakturaNumber,
          accNumber,
          accDate,
          s.paymentDate,
          saldoStart,
          SaldoEnd 
    order by spd.periodStart desc 

Попробуем его в деле.
...
Рейтинг: 0 / 0
11 сообщений из 11, страница 1 из 1
Форумы / Sybase ASA, ASE, IQ [игнор отключен] [закрыт для гостей] / Оптимизация запросов в ASA7
Найденые пользователи ...
Разблокировать пользователей ...
Читали форум (0):
Пользователи онлайн (0):
x
x
Закрыть


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