powered by simpleCommunicator - 2.0.49     © 2025 Programmizd 02
Форумы / Delphi [игнор отключен] [закрыт для гостей] / Медленное получение данных через TFDQuery (FireDAC)
59 сообщений из 59, показаны все 3 страниц
Медленное получение данных через TFDQuery (FireDAC)
    #39122099
Трость
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
Доброе утро.

СУБД MSSQL2008R2
Не могу разобраться, почему выполнение запроса через SSMS выполняется быстро (8 сек.) через FireDAC очень медленно. Строк примерно 140т.

Я понимаю, что выполнение через SSMS и через приложение не одно и тоже. Но запрос элементарный без join и т.п.

Возможно дело в каких либо настройках TFDConnection или TFDQuery?
А возможно это непоправимо т.к. TFDQuery получает данные медленно (буферизация медленная или ещё что...).

Подскажите что можно посмотреть?
...
Рейтинг: 0 / 0
Медленное получение данных через TFDQuery (FireDAC)
    #39122134
Valery_B
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Трость,

На ФаирДАК особо ничего не делал, но предполагаю что:
1. У ФаирДАК такая-же болезнь как и TClientDataSet. Я об этом писал тут . При вызове, который возвращает большое количество информации он будет делать что-то никому не понятное и что-то очень долгое. Торможение равно квадрату возвращённой информации.
2. Наверняка некие "умельцы" тебе сейчас скажут, что возвращать на клиента 150 тыс строк - это не правильно. И то, что ФаирДАК работает медлено - это твоя ошибка, а не ФаирДАКа. Но я тебе такого не говорю.

Ну может к ФаирДАК это и не относится, и там действительно надо какому-то свойство присвоить Значение:=True; А так, это всё основано на очень негативном опыте от TClientDataSet.
...
Рейтинг: 0 / 0
Медленное получение данных через TFDQuery (FireDAC)
    #39122137
Valery_B
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Трость,

Попробуй в новом тестовом проекте сделать тот-же самый запрос через ADO - я уверен, что он пройдёт как и в SMSS за 8 секунд.
...
Рейтинг: 0 / 0
Медленное получение данных через TFDQuery (FireDAC)
    #39122157
Трость
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
Valery_BТрость,

Попробуй в новом тестовом проекте сделать тот-же самый запрос через ADO - я уверен, что он пройдёт как и в SMSS за 8 секунд.

Хм... странно... TADOQuery работает быстро, даже немного быстрее чем через SSMS.
Много отзывов читал про FireDAC, вроде писали что быстрее и т.п. получается при чтении большого количества строк работает медленно 140т. читает 32 сек. а ADO справляется за 8...

Хотелось бы услышать ещё мнения.
...
Рейтинг: 0 / 0
Медленное получение данных через TFDQuery (FireDAC)
    #39122178
Valery_B
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Тростьпри чтении большого количества строк работает медленно 140т. читает 32 сек. а ADO справляется за 8...

Ну 32 секунды вместо 8 - это ещё терпимо. Это "всего-то" в 4 раза медленнее, чем должно. В случае КлиентскогоДатаСета это было бы 3.2 минуты против 8 секунд АДО)

Что за ЦП ? У меня "Коре Йа7" - замена на ещё более быстрый повысит скорость, это 100%:))
Посмотри на загрузку 1 ядра ЦП во время получения данных - он загружен на 100%

Тебе помогут только разработчики ФаирДАК. Но я думаю, что они тебе скажут смотреть п.2 моего ответа )
...
Рейтинг: 0 / 0
Медленное получение данных через TFDQuery (FireDAC)
    #39122180
Valery_B
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Кстати, скорее всего "Тормознутость" - не от количества строк, а от объёма данных.
Если вернуть миллион строк только с одним полем типа Integer, то они засосуться пропорционально быстрее, чем 100тыс но с 10 разными полями.
...
Рейтинг: 0 / 0
Медленное получение данных через TFDQuery (FireDAC)
    #39122189
bk0010
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Мне на Informix помогло отключение fiMeta в FetchOptions и ReadOnly=true - скорость выросла многократно.
...
Рейтинг: 0 / 0
Медленное получение данных через TFDQuery (FireDAC)
    #39122194
vavan
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Valery_Bскорее всего "Тормознутость" - не от количества строк, а от объёма данныхне без этого конечно. как там датасеты/провайдеры формируют датапакет и сколько реаллокаций при этом делают можно предполагать зря что ли я свой мидас/cds переучивал
...
Рейтинг: 0 / 0
Медленное получение данных через TFDQuery (FireDAC)
    #39122214
Трость
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
bk0010Мне на Informix помогло отключение fiMeta в FetchOptions и ReadOnly=true - скорость выросла многократно.

Действительно лучше, вместо 32 сек стало 26... но это далеко от идеала...
...
Рейтинг: 0 / 0
Медленное получение данных через TFDQuery (FireDAC)
    #39122229
Valery_B
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
vavan, учить умершую технологию Midas помоему извращение в 2015)

Что бы абстрагироваться от получения данных раньше я использовал абстрактный класс - TxClientDataSet;
Но теперь, для доступа к данным у меня используется интерфейс IDataSet с 2-3 базовыми свойствами. Что бы не реализовывать кучу свойств в интерфейсе создан под-класс для IDataSet - TDataSetProperties. Фактически, это просто класс с набором строковых свойств.

Таким образом в TDataSet, возвращаются данные полученные вообще не понятно каким способом.
Это гарантирует работу с любой БД.

Вот что получилось:

Код: pascal
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.
TDataSetProperties = class
 private
    FDBName: String;
    FProviderName: String;
    FParams: TParams;
 Public
    Property DBName:String read FDBName write FDBName;
    Property ProviderName: string read FProviderName write FProviderName;
    Property Params: TParams read FParams write FParams;
    Constructor Create;
    Destructor Destroy; Override;
end;


IDataSet = Interface
 ['{A05A188A-F45D-43D0-A410-D8EF6631DBBC}']
  Function Identity : Integer;
  Procedure ApplyUpdates(MaxErrors:Integer);
  Procedure SetParameter(ParamName:String; Value:OLEVariant);
  Procedure OpenOrExecute;
  Procedure OpenOrExecuteAsync(OnTerminate:TDataSetNotifyEvent);
  Procedure CancelAsyncExecution(OnTerminate:TDataSetNotifyEvent);

  Property ProviderName: string read GetProviderName write SetProviderName;
  Property Properties : TDataSetProperties read GetDataSetProperties;
end;

...
Рейтинг: 0 / 0
Медленное получение данных через TFDQuery (FireDAC)
    #39122241
Трость
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
Уж очень интересно, что на это скажет Dmitry Arefiev. По возможности просим ответить...
...
Рейтинг: 0 / 0
Медленное получение данных через TFDQuery (FireDAC)
    #39122247
Valery_B
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Ой, главное свойство не скопировалось :)
Код: pascal
1.
2.
3.
IDataSet = Interface
 ['{A05A188A-F45D-43D0-A410-D8EF6631DBBC}']
 Function DataSet:TDataSet;



А используется так:
Код: pascal
1.
2.
3.
4.
5.
6.
7.
8.
9.
Procedure TForm1.Button1Click(Sender:TObject);
var
 D:IDataSet;
begin
 D:=TDefaultDataSet.Create(Nil);
 D.ProviderName:='Select * from Table1';
 D.OpenOrExecute;
 ShowMessage(D.DataSet.Fields[0].AsString);
end;


В случае с интерфейсами делать D.Free не надо.
...
Рейтинг: 0 / 0
Медленное получение данных через TFDQuery (FireDAC)
    #39122263
Michael Longneck
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Вы там Fetch всех записей делаете? Или не всех? Время очень разное.
...
Рейтинг: 0 / 0
Медленное получение данных через TFDQuery (FireDAC)
    #39122270
Трость
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
Michael LongneckВы там Fetch всех записей делаете? Или не всех? Время очень разное.

Mode = fmAll

Хотя если Mode = fmOnDemand и делаем Query.Last, то скорость можно сказать не отличается
...
Рейтинг: 0 / 0
Медленное получение данных через TFDQuery (FireDAC)
    #39122288
Michael Longneck
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Ну так логично, что сделав Query.Last скорость не будет отличаться. Но SSMS не делает Last.
...
Рейтинг: 0 / 0
Медленное получение данных через TFDQuery (FireDAC)
    #39122294
Трость
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
Michael LongneckНу так логично, что сделав Query.Last скорость не будет отличаться. Но SSMS не делает Last.

Так, и к чему вы клоните? Как можно ещё попробовать?
...
Рейтинг: 0 / 0
Медленное получение данных через TFDQuery (FireDAC)
    #39122302
Glays
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Тростьи делаем Query.Last
А в SSMS тоже все строки выгружаем?

Вообще, пока я бы сказал что Valery_Bвозвращать на клиента 150 тыс строк - это не правильно.
Потому что 150 тысяч строк не подразумевают под собой взаимодействие с человеком, а скорее всего будут обработаны или экспортированы(скорее всего в эксель), а это чаще всего имеет смысл делать силами самого сервера.
...
Рейтинг: 0 / 0
Медленное получение данных через TFDQuery (FireDAC)
    #39122303
Michael Longneck
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Ни к чему. Только к тому, что SSMS фетчит первые N записей и останавливается. Точно также как и FireDac в режиме OnDemand. Таким образом "тормоза" это просто разница между частичным и полным fetch.
...
Рейтинг: 0 / 0
Медленное получение данных через TFDQuery (FireDAC)
    #39122305
Michael Longneck
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Что касается 150 тыс, то если обработка не подразумевает возвратов назад, то надо включить Unidirectional и гнать цикл до конца датасета. И быстрее и памяти много не надо.
...
Рейтинг: 0 / 0
Медленное получение данных через TFDQuery (FireDAC)
    #39122310
igor888
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
Michael Longneck,

Я так и не могу понять, какая разница в Mode в плане чтения 140т. строк.

Вы хотите сказать, что если читать пакетно то скорость увеличится?

--Что касается 150 тыс, то если обработка не подразумевает возвратов назад, то надо включить Unidirectional

В том то и дело, что это ограничения на ровном месте, когда TADOQuery работает не хуже SSMS
...
Рейтинг: 0 / 0
Медленное получение данных через TFDQuery (FireDAC)
    #39122319
Michael Longneck
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Я хочу сказать, что если выполнить запрос, зафетчить первые 200 записей и остановиться (как делает SSMS), это быстрее чем не останавливаться и вычитать из сервера все 140 тыс. Вы понимаете что запрос грубо делится на собственно исполнение и чтение данных? И вторая операция может быть сделана по частям?
...
Рейтинг: 0 / 0
Медленное получение данных через TFDQuery (FireDAC)
    #39122326
Valery_B
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
GlaysПотому что 150 тысяч строк не подразумевают под собой

Ну я сразу так и сказал, наверняка тут будут говорить о не правильности запроса и т.п. :)

В моём случае, а возвращаю координаты всех звёзд, комет и астеройдов в Тентуре (это направо от Большой Медведицы) и прокладываю маршрут своего Пепелаца так, что бы он врезался в эти объекты.
т.е. обсуждение нужно мне 150 тыс строк или нет - это отдельная тема.


Автору темы:
Сделай:
Код: pascal
1.
2.
ADODataSet.First;
While not ADODataSet.Eof do ADODataSet.Next;


Код: pascal
1.
2.
FireDacDataSet.First;
While not FireDacDataSet.Eof do FireDacDataSet.Next;


Разница будет минимальна. ADO(и SSMS) по умолчанию получает все записи сразу без Fetchа и ему подобных.
Хотя сам цикл While not EOF у АДО медленней, чем у ClientDataSet.
...
Рейтинг: 0 / 0
Медленное получение данных через TFDQuery (FireDAC)
    #39122328
Valery_B
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Michael Longneck
(как делает SSMS)

Только SSMS так не делает.
Если показано, что "Запрос выполнен" - то запрос выполнен полностью.
...
Рейтинг: 0 / 0
Медленное получение данных через TFDQuery (FireDAC)
    #39122397
Michael Longneck
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Да, действительно, фетч продолжается в фоне. Однако первые видимые записи он показывает гораздо раньше окончания фетча. Вы на какое время ориентируетесь - на то, что пишет SSMS в строке статуса как время выполения? И что, оно гораздо меньше времени запроса через FireDac при fmAll?
...
Рейтинг: 0 / 0
Медленное получение данных через TFDQuery (FireDAC)
    #39122398
vavan
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Valery_Bучить умершую технологию Midas помоему извращение в 2015я начал ее юзать где-то в 98-99-м и когда проблемы утомили совсем году в 2005-6-м пересел на hyperbase и собственный транспорт, так что дело было уже лет десять как. да возможно и сейчас бы предпочел переучивать хоть что-то готовое чем лепить полностью с нуля. а совсем умрет она не раньше дельфей и проектов на ней построенных
...
Рейтинг: 0 / 0
Медленное получение данных через TFDQuery (FireDAC)
    #39122445
Трость
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
Michael LongneckДа, действительно, фетч продолжается в фоне. Однако первые видимые записи он показывает гораздо раньше окончания фетча. Вы на какое время ориентируетесь - на то, что пишет SSMS в строке статуса как время выполения? И что, оно гораздо меньше времени запроса через FireDac при fmAll?

Медленней, в 4 раза

Вот это:
Код: pascal
1.
2.
FireDacDataSet.First;
While not FireDacDataSet.Eof do FireDacDataSet.Next;


Добавляет ещё пару секунд на обработку.


Уже всё перепробовал, хоть тресни
В общем вопрос открытый, почему FireDAC работает очень медленно при большой загрузке строк (140т. строк). Аж в 4-ре раза медленней чем ADO!
...
Рейтинг: 0 / 0
Медленное получение данных через TFDQuery (FireDAC)
    #39122454
Glays
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Valery_Bпрокладываю маршрут своего Пепелаца
Такой пример покатит, если ты Человек дождя и вводишь все координаты с экрана вручную.
И то, не уверен, что тут нужен фетч всех записей, вполне хватит OnDemand.

Valery_Bт.е. обсуждение нужно мне 150 тыс строк или нет - это отдельная тема.
Считаешь, я опережаю время?
Только когда автор вернётся с вопросом "почему фильтрация/сортировка/расчёт виртуальной колонки/выгрузка в эцих" работает медленно, ему можно будет сказать что он с самого начала был не прав?

ТростьУже всё перепробовал, хоть тресни
Трость, а если не делать Query.Last?
...
Рейтинг: 0 / 0
Медленное получение данных через TFDQuery (FireDAC)
    #39122471
vavan
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Glaysпочему фильтрация/сортировка/расчёт виртуальной колонки/выгрузка в эцих" работает медленнофильтрация/сортировка зафетченного набора данных даже в сотни тысяч записей работает быстро в любом приличном датасете
как работает "расчёт виртуальной колонки" пожалуй зависит от вложенного в это смысла и содержание расчета
что есть "выгрузка в эцих" непонятно но тоже весьма вероятно влияет качество реализации

у меня юзвери порой и сотни тысяч записей с более чем сотней полей на клиента в cds тягают ч/з "мертвый" мидас
...
Рейтинг: 0 / 0
Медленное получение данных через TFDQuery (FireDAC)
    #39122472
Трость
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
Glays,

Про Query.Last не понял...
Можно поподробнее
...
Рейтинг: 0 / 0
Медленное получение данных через TFDQuery (FireDAC)
    #39122484
Glays
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
ТростьGlays,

Про Query.Last не понял...
Можно поподробнее


ТростьХотя если Mode = fmOnDemand и делаем Query.Last
Что происходит если не делать Query.Last?
...
Рейтинг: 0 / 0
Медленное получение данных через TFDQuery (FireDAC)
    #39122562
Фотография Dmitry Arefiev
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Причин может быть много. Присылай на darefiev at da-soft dot com:
1) Отчет об окружении - http://docwiki.embarcadero.com/RADStudio/Seattle/en/DBMS_Environment_Reports_(FireDAC)
2) Дамп таблицы или файл бэкапа БД

PS: Обычно дело в клиенте SQL Server'а и в том как FireDAC выбирает тип курсора.
...
Рейтинг: 0 / 0
Медленное получение данных через TFDQuery (FireDAC)
    #39122686
Трость
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
GlaysТростьGlays,

Про Query.Last не понял...
Можно поподробнее


ТростьХотя если Mode = fmOnDemand и делаем Query.Last
Что происходит если не делать Query.Last?

Если не делаем, то фетчим первые 50 строк (параметр по умолчанию).
Если делаем Query.Last закачиваем 140т. строк.

Всё таки считал что FireDAC в этом плане как минимум не будет уступать.
...
Рейтинг: 0 / 0
Медленное получение данных через TFDQuery (FireDAC)
    #39122696
Трость
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
Dmitry ArefievПричин может быть много. Присылай на darefiev at da-soft dot com:
1) Отчет об окружении - http://docwiki.embarcadero.com/RADStudio/Seattle/en/DBMS_Environment_Reports_(FireDAC)
2) Дамп таблицы или файл бэкапа БД

PS: Обычно дело в клиенте SQL Server'а и в том как FireDAC выбирает тип курсора.

1. Наверное то:
================================
Connection definition parameters
================================
SERVER=90.90.90.90,1433
User_Name=sa
Password=*****
ApplicationName=Architect
Workstation=WIN7NEW
DATABASE=DBTEST5227
MARS=yes
DriverID=MSSQL
================================
FireDAC info
================================
Tool = RAD Studio XE6
FireDAC = 10.0.1 (Build 69712)
Platform = Windows 32 bit
Defines = FireDAC_NOLOCALE_META;FireDAC_MONITOR
================================
Client info
================================
Loading driver MSSQL ...
Loading odbc32.dll driver manager
Creating ODBC environment handle
Searching for ODBC driver ...
Checking for ODBC driver [SQL SERVER NATIVE CLIENT 11.0] ...
Checking for ODBC driver [SQL SERVER NATIVE CLIENT 10.0] ...
Found [SQL Server Native Client 10.0]
Driver Manager version = 03.80.7601.0000
================================
Session info
================================
Current catalog =
Current schema = dbo
Driver name = sqlncli10.dll
Driver version = 10.50.4000
Driver conformance = 3
DBMS name = Microsoft SQL Server
DBMS version = 10.50.1600


2. Не могу предоставить, там конфиденциальные данные. В селекте выбираю 4 поля "идентификатор клиента", "фамилия", "имя", "Отчество".
Код: sql
1.
SELECT [ID], [Fam], [Nam], [Otch] FROM [Clients]



Вы пишите, что есть несколько причин. Приведите хотя бы 2-3, чтоб можно было хоть что нибудь попробовать.

PS: Обычно дело в клиенте SQL Server'а и в том как FireDAC выбирает тип курсора.


Тут совсем ничего непонятно. Какой клиент SQL Server'а?
Вы про нэатив-клиент (Found [SQL Server Native Client 10.0])?
И какой тип курсора подойдёт для него?
...
Рейтинг: 0 / 0
Медленное получение данных через TFDQuery (FireDAC)
    #39122850
Glays
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
ТростьЕсли не делаем, то фетчим первые 50 строк (параметр по умолчанию).
Если делаем Query.Last закачиваем 140т. строк.
Спасибо капитан.
Время выполнения то изменяется?
...
Рейтинг: 0 / 0
Медленное получение данных через TFDQuery (FireDAC)
    #39122863
Трость
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
GlaysТростьЕсли не делаем, то фетчим первые 50 строк (параметр по умолчанию).
Если делаем Query.Last закачиваем 140т. строк.
Спасибо капитан.
Время выполнения то изменяется?

Нет не изменяется, уже писал выше по форуму. Повторюсь

Mode = fmAll
или
Mode = fmOnDemand + Query.Last,

скорость можно сказать не отличается
...
Рейтинг: 0 / 0
Медленное получение данных через TFDQuery (FireDAC)
    #39122865
Glays
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
ТростьНет не изменяется, уже писал выше по форуму. Повторюсь

Mode = fmAll
или
Mode = fmOnDemand + Query.Last,

скорость можно сказать не отличается
Mode = fmAll
или просто
Mode = fmOnDemand
Скорость отличается?
...
Рейтинг: 0 / 0
Медленное получение данных через TFDQuery (FireDAC)
    #39122866
Трость
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
И медленней на пару сек. если:

Mode = fmOnDemand, затем While not FireDacDataSet.Eof do FireDacDataSet.Next;
...
Рейтинг: 0 / 0
Медленное получение данных через TFDQuery (FireDAC)
    #39122869
Трость
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
GlaysТростьНет не изменяется, уже писал выше по форуму. Повторюсь

Mode = fmAll
или
Mode = fmOnDemand + Query.Last,

скорость можно сказать не отличается
Mode = fmAll
или просто
Mode = fmOnDemand
Скорость отличается?

)))) Естественно! Или закачать с сервера 50 строк или закачать 140т. строк.

Вопрос то в другом, почему через SSMS и через приложение на ADO время выполнения занимает 8 сек, а у FireDAC 32 сек.?
И что можно попробовать сделать, чтоб ситуация на FireDAC изменилась, или этого просто невозможно сделать тк FireDAC не рассчитан на такую обработку
...
Рейтинг: 0 / 0
Медленное получение данных через TFDQuery (FireDAC)
    #39122922
Фотография Dmitry Arefiev
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
1) Я так и не понял:
Код: pascal
1.
2.
3.
FDQuery.FetchOptions.Mode := fmOnDemand;
FDQuery.Open;
while not FDQuery.Eof do FDQuery.Next;


и
Код: pascal
1.
2.
ADOQuery.Open;
while not ADOQuery.Eof do ADOQuery.Next;


как различаются по времени ?
2) В запросе:
Код: sql
1.
SELECT [ID], [Fam], [Nam], [Otch] FROM [Clients]


поля как определены ?
3) Попробуй различные значения FetchOptions.CursorKind.
что-то меняется ?
...
Рейтинг: 0 / 0
Медленное получение данных через TFDQuery (FireDAC)
    #39122986
Трость
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
Dmitry Arefiev1) Я так и не понял:
Код: pascal
1.
2.
3.
FDQuery.FetchOptions.Mode := fmOnDemand;
FDQuery.Open;
while not FDQuery.Eof do FDQuery.Next;


и
Код: pascal
1.
2.
ADOQuery.Open;
while not ADOQuery.Eof do ADOQuery.Next;


как различаются по времени ?
2) В запросе:
Код: sql
1.
SELECT [ID], [Fam], [Nam], [Otch] FROM [Clients]


поля как определены ?
3) Попробуй различные значения FetchOptions.CursorKind.
что-то меняется ?

По 1-вы моменту:
FireDAC:
FetchOptions.CursorKind = ckAutomatic
Если Mode = fmAll, открывает примерно за 29,6 сек.
Если Mode = fmOnDemand + Query.Last скорость примерно 29,0 - 29,1 сек.
Если Mode = fmOnDemand + While not Query.Eof do Query.Next; скорость примерно 25,3

ADO:
Если ADOQuery.Open, открывает примерно за 8,0 - 8,5сек.
Если ADOQuery.Open + ADOQuery.Last, скорость примерно 8,1-8,5 сек.
Если ADOQuery.Open +While not ADOQuery.Eof do ADOQuery.Next; скорость 216 сек. ЖЕСТЬ!!!

2
ID - INT автоинкремент, PK (ключевое)
Fam - NVARCHAR(20)
Nam - NVARCHAR(15)
Otch - NVARCHAR(15)

3
etchOptions.CursorKind = ckDefault
Если Mode = fmOnDemand + While not Query.Eof do Query.Next; скорость примерно 29,5

etchOptions.CursorKind =ckDynamic
Если Mode = fmOnDemand + While not Query.Eof do Query.Next; скорость примерно 166 сек.

etchOptions.CursorKind =ckForwardOnly
Если Mode = fmOnDemand + While not Query.Eof do Query.Next; скорость примерно 159сек.

etchOptions.CursorKind =ckStatic
Если Mode = fmOnDemand + While not Query.Eof do Query.Next; скорость примерно 138сек.
...
Рейтинг: 0 / 0
Медленное получение данных через TFDQuery (FireDAC)
    #39123549
Фотография Dmitry Arefiev
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Так это говорит само за себя ...
1) FireDAC честно читает всю выборку на 29 сек. ADO за 216 сек.
FireDAC судя по всему использует дефолтный MSSQL курсор.
3) При одном из других видов курсоров (не ckDefault) возможно время
открытия будет меньше, но полное время выборки будет много больше.
...
Рейтинг: 0 / 0
Медленное получение данных через TFDQuery (FireDAC)
    #39123824
Трость
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
Dmitry ArefievТак это говорит само за себя ...
1) FireDAC честно читает всю выборку на 29 сек. ADO за 216 сек.
FireDAC судя по всему использует дефолтный MSSQL курсор.
3) При одном из других видов курсоров (не ckDefault) возможно время
открытия будет меньше, но полное время выборки будет много больше.

А по Вашему мнению, почему SSMS вопрос выполняет 8сек.? он тоже грузит "нечестно"?
...
Рейтинг: 0 / 0
Медленное получение данных через TFDQuery (FireDAC)
    #39123851
Фотография X-Cite
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Трость,

Сервер MSSQL и SSMS запущены на одной машине?
Есть вероятность что данные передаются через SharedMemory, все одно быстрее чем по TCP/IP
...
Рейтинг: 0 / 0
Медленное получение данных через TFDQuery (FireDAC)
    #39123941
Valery_B
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Трость, или как тебя там по имени ?

1. FireDac.Open занимает 30 секунд. Тут ты вряд ли что-то сделаешь.
2. ADO.Open занимает 3 секунды(у меня). Тут делать ничего не надо.
3. Что касается While not ADO.Eof - жесть. Да, жесть так жесть. Но это не вина АДО, это такая "фича" от разработчиков Delphi 5 (!)
4. О других багах АДО я пытался написать тут

Попробуй сделать так:
Код: pascal
1.
2.
3.
4.
5.
6.
7.
8.
9.
10.
11.
var
 X:Integer;
 MyValue:OleVariant;
begin
ADOQuery1.RecordSet.MoveFirst;
for x:=0 to 150000-1 do
  begin
   ADOQuery1.Recordset.MoveNext;
//   MyValue := ADOQuery1..Recordset.Fields['MyField'].Value;
  end;
end;


У меня это занимает 110 мс. Если разкоментить - то 520 мс.
...
Рейтинг: 0 / 0
Медленное получение данных через TFDQuery (FireDAC)
    #39123943
Valery_B
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
А для тех, у кого нет таблицы со 150,000 строками может сделать такой запрос:

Код: sql
1.
2.
3.
select top 150000 * 
from sys.objects a
cross join sys.objects b
...
Рейтинг: 0 / 0
Медленное получение данных через TFDQuery (FireDAC)
    #39123973
LSV
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Попробуй сделать так:Какое-то идиотское усложнение. Почему не Last ?
...
Рейтинг: 0 / 0
Медленное получение данных через TFDQuery (FireDAC)
    #39123990
Фотография kdv
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
LSV,

у автора вообще медленный газ. Он никак не может понять, что

1. у запроса есть время выполнения на сервере, до выдачи первой записи клиенту.
2. датасет на клиенте, в зависимости от того, как написан клиент и датасет, и от настроек, может
а) показать первые несколько записей, дальше остановиться (или продолжить выборку записей в фоне, как автору уже сказали про SSMS)
б) считать в кэш все записи, только потом их "показать".

Соответственно, будет разное время 1+2а и 1+2б.
Дальше. Если автор пишет про цикл while not Eof do Next, значит он предполагает ПОСЛЕДОВАТЕЛЬНУЮ обработку. А для этого буферизация выбираемых записей не нужна. Буферизация однозначно займет память (все 150к записей на клиента) и также увеличит время. Делает-ли буферизацию SSMS? Скорее всего нет.
Если же нужна оценка выкачки всех записей в кэш датасета, то действительно нужен Last. А если нужен цикл while с обработкой записей, тогда кэшировать датасет не нужно.

Мне больше другое интересно - почему открытие "простого запроса" (без джойнов и т.д.) занимает 8 секунд в SSMS? Если тупо написать select * from table хоть с миллионом записей, первые записи должны быть показаны МГНОВЕННО, речь должна идти про миллисекунды, а не секунды.
Вот на таком запросе и надо сравнивать SSMS и FireDAC (с соответствующими настройками).
...
Рейтинг: 0 / 0
Медленное получение данных через TFDQuery (FireDAC)
    #39124013
Valery_B
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
kdvпочему открытие "простого запроса" (без джойнов и т.д.) занимает 8 секунд в SSMS?

Потому что SMSS не использует ни FireDac, ни TClientDataSet.
Там скорее всего ADO.Net.

Это же интересно и автору темы.
Точнее, сомневаюсь что ему интересно. Главное - что бы у него работало так же. Но не работает.

А вообще, сначала лучше попробуй сделать сам, прежде чем наезжать на автора темы.
...
Рейтинг: 0 / 0
Медленное получение данных через TFDQuery (FireDAC)
    #39124023
Фотография kdv
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Valery_BПотому что SMSS не использует ни FireDac, ни TClientDataSet.
Там скорее всего ADO.Net.
какая разница. механизмы выборки у всех серверов и клиентов одинаковы. Я имею в виду - выполнить запрос, выбрать запись, и т.д.
Valery_BА вообще, сначала лучше попробуй сделать сам
я с MS SQL не работаю. Только с InterBase и Firebird. К ним есть штук 20-30 разных компонент доступа, и штук 8 разных инструментов разработчика (типа SSMS), в которых все это проверяется практически моментально.
В соответствующих форумах уже давно сравнивали FireDAC, IBX, dbExpress, FIBPlus, и др. компоненты на скорость выборки.
Valery_Bпрежде чем наезжать на автора темы
я не наезжаю, я констатирую. ему объясняют смысл уже вторую страницу темы. А он как будто не читает ответы.
...
Рейтинг: 0 / 0
Медленное получение данных через TFDQuery (FireDAC)
    #39124056
vavan
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
kdvкакая разница. механизмы выборки у всех серверов и клиентов одинаковы"мощно задвинул, внушает" (С)
...
Рейтинг: 0 / 0
Медленное получение данных через TFDQuery (FireDAC)
    #39124084
Фотография kdv
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
vavan"мощно задвинул, внушает" (С)
прошу назвать концептуальные отличия у разных серверов и клиентов в схеме prepare->execute->fetch. Или хотя бы execute->fetch.
...
Рейтинг: 0 / 0
Медленное получение данных через TFDQuery (FireDAC)
    #39124108
Фотография X-Cite
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Valery_BТам скорее всего ADO.Net.

Код: sql
1.
2.
3.
4.
5.
6.
7.
8.
9.
10.
SELECT
  des1.client_interface_name,
  dec1.net_transport,
  dec1.protocol_type
FROM
  sys.dm_exec_sessions AS des1
  JOIN sys.dm_exec_connections AS dec1
    ON dec1.session_id = des1.session_id
WHERE
  des1.session_id = @@SPID


Скорее всего .Net SqlClient Data Provider
...
Рейтинг: 0 / 0
Медленное получение данных через TFDQuery (FireDAC)
    #39124122
vavan
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
kdvпрошу назвать концептуальные отличия у разных серверовна столь высоком уровне концептуально они конечно все субд а на практике под капотом такого наверчено может быть что ожидать безусловного мгновенного отклика увы не приходится
...
Рейтинг: 0 / 0
Медленное получение данных через TFDQuery (FireDAC)
    #39124175
Фотография kdv
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
vavan а на практике под капотом такого наверчено может быть
про это я не говорю, и с этим не спорю, оптимизаторы у всех разные, но еще раз подчеркиваю, что самый простой запрос для тестирования скорости выборки, для всех СУБД выполняемый максимально быстро, это
select * from table.
Т.е. одна таблица, никаких условий отбора, группировок, сортировок, серверных курсоров и всего такого.
Такой запрос готов выдавать записи за миллисекунды. А вот уже сколько времени будут выдаваться записи, зависит от многих факторов, включая сеть, если курсор серверный, компоненты, и т.д.
...
Рейтинг: 0 / 0
Медленное получение данных через TFDQuery (FireDAC)
    #39124194
Michael Longneck
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Вообще деталей множество. Если в запросе блобы? У SSMS например по умолчанию все строки не более 256 символов в показе (не знаю хранит ли он полные строки). И.т.д. Записи он буферизирует - иначе бы грид для показа не прокручивался в обе стороны.
...
Рейтинг: 0 / 0
Медленное получение данных через TFDQuery (FireDAC)
    #39124422
rgreat
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Я правильно понял что автор сравнивает
Код: pascal
1.
2.
FireDacDataSet.First;
While not FireDacDataSet.Eof do FireDacDataSet.Next;


и
Код: pascal
1.
2.
ADODataSet.First;
ADODataSet.Last;



Где 1-й последовательно выкачивает все 140 т.з, а второй 50 первых+50 последних?
...
Рейтинг: 0 / 0
Медленное получение данных через TFDQuery (FireDAC)
    #39124469
Фотография defecator
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Модератор форума
rgreatЯ правильно понял что автор сравнивает
Код: pascal
1.
2.
FireDacDataSet.First;
While not FireDacDataSet.Eof do FireDacDataSet.Next;


и
Код: pascal
1.
2.
ADODataSet.First;
ADODataSet.Last;



Где 1-й последовательно выкачивает все 140 т.з, а второй 50 первых+50 последних?
а с чего Last вычитывает именно 50 последних ?
...
Рейтинг: 0 / 0
Медленное получение данных через TFDQuery (FireDAC)
    #39124477
Michael Longneck
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Последние 50 выкачивает только TFDTable в режиме LiveWindow. Там особая уличная магия. TFDQuery так не делает.
...
Рейтинг: 0 / 0
Период между сообщениями больше года.
Медленное получение данных через TFDQuery (FireDAC)
    #40104849
Michael Longneck
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Вот и я наткнулся на эту проблему в совсем ином разрезе. MSSQL, FireDac, D10.4.2, MS ODBC Driver 17.

Проблема была fetch'е запросов по 1 записи, даже не содержащих блобов в середине

Решилось так:
1 - тип курсора Forward Only.
2 - убрать в в исходниках выставление CUSROR_OPTIONS - Fast Forward Only - иначе принудительный серверный тип курсора (8)
3 - после закрытия стейтмента выставить ROW_ARRAY_SIZE = 1, в противном случае всё свалится опять в серверный курсор. Стейтмент открывается при ROW_ARRAY_SIZE = 1 и только потом, перед fetch выставляется правильный ROW_ARRAY_SIZE (это FireDac и так делает)

В итоге чтение происходит порциями, указанными в FetchOptions а не всегда по 1. На VPN есть выигрыш.
...
Рейтинг: 0 / 0
59 сообщений из 59, показаны все 3 страниц
Форумы / Delphi [игнор отключен] [закрыт для гостей] / Медленное получение данных через TFDQuery (FireDAC)
Целевая тема:
Создать новую тему:
Автор:
Закрыть
Цитировать
Найденые пользователи ...
Разблокировать пользователей ...
Читали форум (0):
Пользователи онлайн (0):
x
x
Закрыть


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