Гость
Целевая тема:
Создать новую тему:
Автор:
Форумы / Сравнение СУБД [игнор отключен] [закрыт для гостей] / SQL Server VS OleDB in ASP / 14 сообщений из 14, страница 1 из 1
27.01.2009, 15:27
    #35780318
genixxx
Гость
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
SQL Server VS OleDB in ASP
Добрый день, уважаемые!
Прошу прощения сразу, если что-то не там создал или неправильно назвал тему, старался как мог, но тут пишу первый раз =)

Существует проблема следующего рода - работа в фирме осуществляется по программам другой организации, от которой мы зависим, а они используют FoxPro. Следовательно, все данные хранятся у нас в табличках DBF и там и сям.
Но по нужде разработки своих некоторых программ приходиться использовать эти вод БД из файлов. Подключаюсь к папке с файлами через OleDB провайдер, особых проблем не составляет.

Но вот какая проблема - временами запросы выполняются очень долго и сотрудникам, для кого мы пишем программы, приходится по две минуты, а то и больше, ждать реакции компьютера. А данных то не так много!
Еще есть такой факт, что таблички созданы не нами, но для них сгенерированы ключи, которые по идее обеспечивают быстродействие. (Но тут есть вопрос - использую ли я эти ключи, выполняя произвольный запрос напрямую или мне надо конкретно в подключении указывать существование ключей?)

Приведу конкретный пример:
Задача - подсчет статистики по некоторым параметрам за некоторый промежуток. Файла, из которых производить выборку, всего три:
akt_det - 200 Mb
akt_eksp - 10 Mb
spr_med - 10 Kb

Но для построения статистики нужно выполнить около 15 отдельных COUNT-запросов, а если их делать напрямую к этим файлам, времени уходит минут 40 только за один месяц. Для ускорения этой работы сделал таблицу в SQLExpress и в нее перегоняю сначала все необходимые данные за промежуток, а потом уже работаю с скл-сервером.
Такой ход дал неплохие результаты - время подсчета статистики используя уже готовую временную базу около 5 секунд, в отличие от прошлых 40 минут.
Но выполнения вот этой конвертации занимает больше всего времени - 35 секунд, из которых 34,78 приходится на запрос СЕЛЕКТ, получающий данные, который я тут привел:
Код: plaintext
1.
2.
3.
4.
5.
SELECT prz_spv, cd_prov, vid_priem, vp, dat_s, dspc, polis, ad.cd_akt 
FROM akt_eksp ae
LEFT JOIN akt_det ad ON ad.cd_akt = ae.cd_akt AND ad.vid_prov= 1 
LEFT JOIN spr_med ON spr_med.cd_eksp = ad.cd_eksp 
WHERE ae.vid_akt =  1   AND " +
                        "ae.dat_s between {^" + tempDate.ToString("yyyy-MM-dd") + "} AND {^" + tempDate.AddMonths(1).ToString("yyyy-MM-dd") + "}");

Вроде бы как бы запрос то не шибко долгий должен быть, никаких очень тугих операторов не использовано, всего то парочка аутер джойнов.

Так вот в чем беда - аналогичная программа, написанная на фокспро (но чуточку нам неподходящая) делает аналогичную выборку за 10 месяцев за полторы минуты, а всего один запрос мой (выше) занимает 8 минут

Вот что я хотел спросить - что можно оптимизировать в данном случае? И почему программа на фоксе, оперируя теми же данными, делает это в несколько раз быстрее? Подскажите кто чем может, пожалуйста, в какую сторону копать - хотя бы про что почитать или изучить, я ведь дофига чего не знаю стопудово. Собсно поэтому и спрашиваю у вас =)
...
Рейтинг: 0 / 0
27.01.2009, 16:04
    #35780438
Yo.!
Гость
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
SQL Server VS OleDB in ASP
"аналогичная программа, написанная на фокспро" делает выборку из дбф, а вы эту выборку из дбф или уже из SQLexpres ? если из SQLexpress расставте хотя бы индексы на колонки участвующие в запросе, а вообще смотрите план запроза, там все ответы ...

что до выборки из дбф для перегона то судя по 34 секундам движек который работает с дбф (оледб наверно) не смог по индексам отфильтровать, поэтому кроме индексов качает с файл-сервера все 200 мб akt_det.dbf и на месте уже джоинит и фильтрует.
...
Рейтинг: 0 / 0
28.01.2009, 09:35
    #35781710
genixxx
Гость
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
SQL Server VS OleDB in ASP
Yo.!,

В том то и дело, что из ДБФ, также как и прога на фоксе. Только она делает это быстрей.
А можно поподробнее где посмотреть план запроса, я не очень понял что это такое =)

Насчет индексов это Вы хорошо напомнили, добавил сейчас в индекс поля, по которым делаю выборку (получилось плюс одно-два поля в индексах этих таблиц), но прироста производительности это почему-то не дало... Сейчас почитаю че-нить про эти индексы, а то чет первый раз с ними работаю и не знаю с чем их едят =(
...
Рейтинг: 0 / 0
28.01.2009, 09:41
    #35781733
Зайцев Фёдор
Участник
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
SQL Server VS OleDB in ASP
...
Рейтинг: 0 / 0
28.01.2009, 10:43
    #35781926
Sergey Orlov
Участник
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
SQL Server VS OleDB in ASP
Попробуйте between заменить на > и < . И честно говоря я бы все данные загружал бы в SQL и там уже выдергивал бы данные
...
Рейтинг: 0 / 0
28.01.2009, 11:51
    #35782193
genixxx
Гость
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
SQL Server VS OleDB in ASP
Sergey Orlov,

Насчет полностью все таблицы перегнать в СКЛ я тоже уже задумывался, но они обновляются каждый день и даже иногда несколько раз в день, поэтому возникает проблема актуальности информации в СКЛ, ее надо поддерживать как-то, но не перегонять каждый раз при запросе полностью все нужные таблицы, а как-то искать сделанные изменения что ли. В общем думаю над этим.

После того как добавил в индексные столбы те, которые использую в запросе, один раз у меня запрос за большой промежуток выполнился за 4:30 минуты.

Попробовал использовать < > вместо between, на одномесяном запросе результат выдало за 28 секунд, а то, которое за долгий промежуток сейчас выполнилось за 6:33 минуты...


Я вот что не понимаю - почему каждый раз я получаю одинаковые резльтаты за разные промежутки времени? Причем я бы еще мог понять, если бы первый раз было долго, а последующий быстро (ну на какое-нить кэширование бы списал), или даже если бы первый быстро, а последующие дольше и дольше (подумал бы что какие-то массивы слишком большими становятся и фрагментируются в памяти или чета типа того), но блин я выполняю одни и те же действия (очищаю базу СКЛ, запрос к ДБФ, вставляю в СКЛ) и это занимает то 4 минуты, то 8 минут, то 6, то вообще к черту зависает и отмораживается через час о_О
Из-за чего такое может быть?
...
Рейтинг: 0 / 0
28.01.2009, 12:18
    #35782276
genixxx
Гость
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
SQL Server VS OleDB in ASP
Зайцев Фёдор,

Спасибо за ссылку, прочитал пока мельком. Я так понял, что в индекс не очень желательно добавлять столбец с типом данных datetime, ибо это не целое число, но все равно же быстрее должен быть поиск по индексам... У меня этот файл индексов получился 20 мегабайт (вместе с теми, которые там уже были), наверно это тоже много... Интересно, может ли такое быть, что ОлеБД провайдер мой просто не использует по умолчанию эти индексы, а грузит целиком? Может где-то в настройках это указывается... Сейчас попробую их удалить и сравнить время запроса. =)
...
Рейтинг: 0 / 0
28.01.2009, 13:20
    #35782550
Изопропил
Участник
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
SQL Server VS OleDB in ASP
genixxx,

а какой OLEDB провайдер используете?
...
Рейтинг: 0 / 0
28.01.2009, 16:44
    #35783437
Yo.!
Гость
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
SQL Server VS OleDB in ASP
ну варианта два - или вы шлете не такой запрос какой шлется из фокспро или оледб не умеет работать с дбф через индексы и скачивает его весь на локальный комп.
...
Рейтинг: 0 / 0
29.01.2009, 13:56
    #35785461
genixxx
Гость
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
SQL Server VS OleDB in ASP
Изопропил,

VFPOLEDB.1 провайдер использую конечно же, других вроде нет для фокспро =)


Удалил я все-таки индексы временно и проверил увеличится ли время запроса... Нифига оно не увеличилось! Вывод - индексы не используются.

Чтобы использовать индексы с данным провайдером необходимо после установления соединения прописать команду на их использование, напрмиер такую

Код: plaintext
OleDbCommand cmd1 = new OleDbCommand("execscript(\"USE d:\\kach\\dbf\\akt_det.dbf IN  10  ALIAS akt_det ORDER cd_akt OF akt_det.cdx\")", conn);

Время запроса сократилось раз в 6, но теперь обнаружилось другое узкое место - циклический инсерт.

Итого селект теперь занимает 1 минуту, а инсерт 3,5. Как можно это ускорить?

ПОсмотрел BULK INSERT команду, в принципе не очень сложно, но единственное что непонятно - как сделать этот самый файл из дбф, чтобы потом его балкинсертнуть в скл. Команда SELECT * INTO OUTFILE не поддерживается фокспро, поэтому пока нет идей как быть...

Еще нашел какое-то консольное приложение datapump, которое позволяет быстро копировать из ДБФ в СКЛ, но сколько я в инете не искал, не могу нигде скачать =(
Ни у кого нет здесь этого файлика? Или есть другие способы ускорить инсерт?
...
Рейтинг: 0 / 0
29.01.2009, 16:03
    #35785949
Sergey Orlov
Участник
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
SQL Server VS OleDB in ASP
Попробуй закачать данные в SQL и там посмотреть план выполнения твоего запроса, у тебя где-то идет полный скан таблицы, причем судя по всему не один...
...
Рейтинг: 0 / 0
29.01.2009, 17:04
    #35786212
genixxx
Гость
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
SQL Server VS OleDB in ASP
Sergey Orlov,

Прошу прощения, почему вы так решили? Я вот недавно говорил, что теперь селект запрос делается за 5 секунд, это уже допустимо, индексы используются, так что здесь все нормально.

А вот с BULK iNSERT непонятки остались. Я наконец сделал файл вручную из того что получилось, а потом с горем пополам научился считывать его балк инсертом.
Но скорость работы BULK INSERT в отличие от обычного циклического инсерт у меня получилась аж в два раза больше! Почему так? Все же везде говорят, что это очень быстрый метод...

Приведу код своего балкинсерта:

BULK INSERT akt_temp FROM 'C:\\test.txt'
WITH (
BATCHSIZE = 5,
KEEPNULLS,
DATAFILETYPE = 'char',
FIELDTERMINATOR = ',',
ROWTERMINATOR = ';',
LASTROW=" + dt_temp.Rows.Count + "
)
...
Рейтинг: 0 / 0
29.01.2009, 18:40
    #35786468
alexeyvg
Участник
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
SQL Server VS OleDB in ASP
genixxxЕще нашел какое-то консольное приложение datapump, которое позволяет быстро копировать из ДБФ в СКЛ, но сколько я в инете не искал, не могу нигде скачать =(
Ни у кого нет здесь этого файлика? Или есть другие способы ускорить инсерт?Для загрузки данных в из ДБФ в СКЛ можно использовать DTS, или в версиях начиная с 2005 - SSIS.

Если объём данных небольшой, то загрузка этим средством будет быстрая.
...
Рейтинг: 0 / 0
30.01.2009, 11:55
    #35787615
genixxx
Гость
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
SQL Server VS OleDB in ASP
В общем разобрался я со всем этим делом, кажется... В итоге получилось, что все-таки балк инсерт хорошо работает, просто надо было в файл лучше записывать сразу построчно, а я делал не очень правильно и долго.
В общем в результате всех этих оптимизаций запрос, который у меня когда-то работал 52 минуты, сейчас выполняется за 48 секунд. Если бы еще использовать сразу склсервер, а не делать каждый раз предварительно кэш, то были бы те самые 7 секунд.

Всем спасибо за советы и ответы!
...
Рейтинг: 0 / 0
Форумы / Сравнение СУБД [игнор отключен] [закрыт для гостей] / SQL Server VS OleDB in ASP / 14 сообщений из 14, страница 1 из 1
Найденые пользователи ...
Разблокировать пользователей ...
Читали форум (0):
Пользователи онлайн (0):
x
x
Закрыть


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