LINUX.ORG.RU

Java vs PL/SQL - исследование производительности


0

0

Автор поставил вполне реальную (не синтетическую) задачу и решил её при помощи PL/SQL, Java, Python. Результаты довольно интересны: 1) Решение на PL/SQL заняло 24 сек. 2) Прямой перенос алгоритма с PL/SQL на Java и Python дал результат 7.8 cек и 31 сек. Соотвественно 3) Незначительное изменение алгоритма, с целью более полного использования возможностей языков (в частности применение HashMap) еще дальше улучшило результаты: Java - 3.5 сек, Python 12.5 сек. 4) Прогноз автора исследования, что если еще поколдовать с алгоритмом то можно добиться 2.4 секунды на Java. Естественно колдовство такое, что на PL/SQL его никак не положить.

В качестве базы данных использовался Oracle 10XE

Итог исследования таков - перенос логики связанной с обработкой данных из RDBMS на прикладной уровень дает значительный прирост скорости и это стоит учитывать.

В подробностях основная ссылка на исследование.

Вот тут ответы автора на возражения: http://homepage.mac.com/s_lott/iblog/...

>>> Подробности

★★

Проверено: svu ()
Ответ на: комментарий от anonymous

>Автору явно нужно почитать Кайта для начала. Код на PL/SQL написан сознательно или несознательно неоптимально. Для циклов предпочтительно использовать BULK COLLECT, да и бежать по двум вложенным циклам, это нечто ... Обычно такие вещи выносятся в один разумный запрос, с использованием аналатики, например. Так что тесту - низачот. PS А юнит-тесты для PL/SQL тоже пишутся на УРА

Напиши плиз свой вариант, запощу автору посмотрим на прибавку скорости.

redbaron ★★
() автор топика
Ответ на: комментарий от anonymous_IV

This is an ASPCC (American Society for the Prevention of Cruelty to Computers) Certified site. No Intel hardware or Microsoft software were used in the creation of these materials

enormous
()
Ответ на: комментарий от anonymous

> а вот за счет гоняния данных по JDBC можете сильно проиграть.

+1. Как правило, сервер приложений офигенно быстро способен перемесить данные, но расходы на фетч больших рекордсетов сжирают весь перформанс.

> ORM типа hibernate, который в курсе различий разных субд

По поводу различий субд пытался внушить немцу - автору jabberd,когда его детище с мускуля на постгрес переводил. Он согласился, что DB-specific escape strings - зло, и добавил, что ой blya nafig столько кода месить - отложим до следующего мажор-релиза. Так что различия СУБД (хотя бы в случае EAV, который я в нескольких проектах успешно юзаю несмотя на слюнобрызги зло-пыхпых-пыхателей) - выносить из логики подальше. в отдельный слой.

> перфоменс будет с ним ниже плинтуса

Ну еще бы :)

Kardinal
()
Ответ на: комментарий от anonymous

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

С одной стороны, я с тобой согласен. С другой стороны, пожертвовать десятком-другим процентов перформанса в угоду code-maintainability - ну оооочень большое искушение :)

Kardinal
()
Ответ на: комментарий от redbaron

>>Автору явно нужно почитать Кайта для начала. Код на PL/SQL написан сознательно или несознательно неоптимально. Для циклов предпочтительно использовать BULK COLLECT, да и бежать по двум вложенным циклам, это нечто ... Обычно такие вещи выносятся в один разумный запрос, с использованием аналатики, например. Так что тесту - низачот. PS А юнит-тесты для PL/SQL тоже пишутся на УРА

>Напиши плиз свой вариант, запощу автору посмотрим на прибавку скорости.

Где можно почитать о постановке задачи? Желательно также иметь под рукой и скрипты для создания таблиц и данные для заливки.

anonymous
()
Ответ на: комментарий от anonymous

Наблюдение первое. Автор теста не понимает, для чего нужен PL/SQL или вообще SQL.

Наблюдение второе. Процедура пытается найти кол-во точных совпадений man-invoice, дупликатов таких совпадений, и то же самое для примерных совпадений. Почему автор теста не сделал это через пару временных таблиц (или как они зовутся в Оракле) - я не в курсе. В Postgres, скажем, это делается следующим образом:

1) Выбираем в первую временную таблицу номера invoices для точного совпадения 2) Выбираем во вторую временную таблицу номера invoices для примерного совпадения 3) Используя group by, находим кол-во уникальных invoices (having count(*) = 1) и дупликатов (... > 1) в первой таблице (это два запроса) 4) Используя group by, находим кол-во уникальных invoices и дупликатов во второй таблице (это еще два запроса)

Итого - 6 запросов и никаких циклов. На 4K записей это будет примерно 50..300 msec - в зависимости от железа и сервера.

Причем тут Java/Python/C - я просто не знаю.

HappySquirrel
()
Ответ на: комментарий от redbaron

>На больших одъемах данных производительность первого и второго вариантов несравнима. Простой пример - выполнить процедуру FOR EACH ROW для UPDATE по таблице с несколькими миллиардами записей.

>А разве такая процедура должна проводиться регулярно?

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

>Понимаю разово при апгрейде версии софта(схемы), но что б в повседневной работе перебирать все записи и их обновлять...

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

stellar
()

Предсказуемо. Размещение ЛОГИКИ в базе -- зло. База -- она ДАННЫХ. А логика должна быть в стороне.

Не говоря уж о том, что логику в приложении можно 1) легко увидеть, вылив исходники 2) модифицировать программистом, которых больше чем DBA 3) отслеживать тем же cvs, в отличи от хранимых процедур (ага, найди версию хранимой процедуры двухмесячной давности и скажи, какие изменения и почему в нее вносились)

Zulu ★★☆☆
()
Ответ на: комментарий от Zulu

что? Чтобы исходники хранимых процедур держали в текстовых файлах? Н у так это называется культура:) Я, например, держу все *.sql для создания таблиц в текстовых файлах с исходниками. Да, и проблемы в Makefile создать правило для изменеия ХП нет.

krum
()
Ответ на: комментарий от Zulu

>Размещение ЛОГИКИ в базе -- зло. База -- она ДАННЫХ. А логика должна быть в стороне.

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

stellar
()
Ответ на: комментарий от stellar

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

А ещё есть мнение, что логика в первую очередь должна быть в голове. От этого и идут все проблемы, что ДБА-шнегов, что С++-негов и прочих сочувствующих, что не способны асилить абстракции и испытывают незаглушаемую потребность в костылях. Только Лисп и массовые расстрелы спасут мир.

Gharik
()
Ответ на: комментарий от krum

Ещё один юный критикал. Я с рождения участвую в крупнейшем проекте, сама история человечества в котором - всего лишь незначительная составляющая.

"Пожелание удачи напоследок" в стиле Луговского, уж извиняй, писать не буду.

Gharik
()
Ответ на: комментарий от Gharik

>Ещё один юный критикал. Я с рождения участвую в крупнейшем проекте, сама история человечества в котором - всего лишь незначительная составляющая.

В биореакторе с самого рождения? Сочувствую....

anonymous
()
Ответ на: комментарий от anonymous

> В биореакторе с самого рождения? Сочувствую....

Мышление Ваше примитивно и приземлённо, эволюция вселенной - что может быть крупнее? =)

Gharik
()
Ответ на: комментарий от Gharik

>Мышление Ваше примитивно и приземлённо, эволюция вселенной - что может быть крупнее? =)

Осталось только выяснить, что же такое венец эволюции вселенной; уж не биореактор ли? ;)

anonymous
()
Ответ на: комментарий от anonymous

> Осталось только выяснить, что же такое венец эволюции вселенной; уж не биореактор ли? ;)

Антропоцентрическая Вселенная... старо и глупо...

Gharik
()
Ответ на: комментарий от Gharik

Так по сути есть что сказать? Или как обычно? По собственному опыту скажу, что в итоге реляционная СУБД оказывается более удачным решением, чем объектная типа fastdb, или key-value типа qdbm. Естественно там, где структуры данных простые можно и key-value использовать. Чаще всего разговоры про тормоза связаны с плохим знанием СУБД. Была часть кода, в который было много запросов, там я не использовал связанные переменные, а каждый раз строил запрос заново. Долго матерился, почему тормозит, как только стал использовать связанные переменные, все тормоза пропали.

krum
()
Ответ на: комментарий от krum

> Так по сути есть что сказать? Или как обычно? По собственному опыту скажу, что в итоге реляционная СУБД оказывается более удачным решением, чем объектная типа fastdb, или key-value типа qdbm. Естественно там, где структуры данных простые можно и key-value использовать. Чаще всего разговоры про тормоза связаны с плохим знанием СУБД. Была часть кода, в который было много запросов, там я не использовал связанные переменные, а каждый раз строил запрос заново. Долго матерился, почему тормозит, как только стал использовать связанные переменные, все тормоза пропали.

Я без руля вообще, что там и куда в данной конкретной базе данных, но скажу просто - когда начинают забивать микроскопом гвозди, хорошего получается мало. Так и с объединением логики и данных - пока есть выигрыш за счёт оптимизации структуры, запросов и прочей херни - жить ещё кое-как можно на итоговом компромиссе. Но зачем такое делать, если можно логику вынести отдельно и получить ещё больший прирост производительности к уже имеющемуся?

И, тем более, писать фактически софт на кривом языке, предназначенном для совершенно иного и упрятанном в недра __СУБД__ есть великий маразм, не оправдываемый ничем. Хотя "энтерпрайзам", стремящимся побыстрее запрячь, вместо реально быстрой езды, сего и не понять.

Критерий-то у нас один, по большому счёту - производительность. А в итоге - всё больший пиз**ц с каждым годом в этом плане, уже не покрываемый и железом.

Gharik
()
Ответ на: комментарий от anonymous_IV

> заколачивают pl/sql-ем любые видимые ими гвозди

+1

Только стоит добавить, что страдают этим как правило бывшие физики и слесари перешедшие в "программисты" после трехнедельных "курсов по ораклу" :-)

no-dashi ★★★★★
()
Ответ на: комментарий от no-dashi

Ну так вот в чём корень всех зол, в неопытности! Я также очень сомневаюсь, что освоив за 3 недели тот Lisp или Haskell,уже не говоря о C и C++, вы напишете что-то стоящее. А г. Gharik дальше своего носа/десктопа ничего не видит.

krum
()
Ответ на: комментарий от no-dashi

>заколачивают pl/sql-ем любые видимые ими гвозди

гвозди не звозди, но иногда производительность существенно поднимается при переносе отдельных критических кусков логики в pl/sql. Хотя это, конечно, костыль.

vtVitus ★★★★★
()
Ответ на: комментарий от vtVitus

Глянул код на PL/SQL - уссался от смеха. Автору редиску на необитаемом острове выращивать, а не сравнения проводить. P.S. BULK + COLLECTION спасут честь PL/SQL. P.P.S. Хотите на С напишу так, что на GW BASIC'е быстрее работать будет?

anonymous
()
Ответ на: комментарий от stellar

>>На больших одъемах данных производительность первого и второго вариантов несравнима. Простой пример - выполнить процедуру FOR EACH ROW для UPDATE по таблице с несколькими миллиардами записей.

>>А разве такая процедура должна проводиться регулярно?

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

Вообще в доках по любой субд пишут нечто вроде "Вообще то мы тоже умеем курсоры и циклическую обработку записей, тока включите мозг, и не используйте бо SQL быстрее". Никакой FOR EACH не отработает быстрее запроса UPDATE ... WHERE на нормально индексированной таблице. И практически любой алгоритм можно решить на PL/SQL без использования курсоров. Потому все что касабельно массовой обработке данных лучше писать на pl/sql. ИМХО Заставили PL/SQL бегать на карачках и раструбили о том что ява - это круто. Дешевый пиар.

anonymous
()
Ответ на: комментарий от Gharik

О чем вы вообще спорите?? Что - 4000 записей на любом языке обрабатываются 3-4 сек, и автор этим гордится? Вы что - совсем считать не умеете? Я же уже писал выше - максимальное время при грамотной реализации этой задачи - 300ms, это если на старой 500MHz машине гонять. Хоть примерно прикиньте: мы даже не говорим о доступе к диску, так как данные такого размера полностью влезают в кеш.

> И, тем более, писать фактически софт на кривом языке, предназначенном для совершенно иного и упрятанном в недра __СУБД__ есть великий маразм, не оправдываемый ничем. Хотя "энтерпрайзам", стремящимся побыстрее запрячь, вместо реально быстрой езды, сего и не понять.

Вообще, все споры подобного типа закончились примерно в 1996..1998гг. Вам что - об этом не сказали? И закончились полной победой SQL как языка, оптимизированного для массовой обработки.

Тем, кто все еще кричит про быструю обработку на клиенте, рекомендую все-таки выучить SQL. Этот горе-тестер, например, просто переписал с Java на SQL свою задачу. Это как на автомобиле ехать задним ходом. Ну не понял он - как работает SQL. Не слышал никогда про GROUP BY .. HAVING .. Потому и результат идиотский. 3..4 секунды на обработку всего 4K+ записей?? Меня бы с работы выгнали за такие результаты..

HappySquirrel
()
Ответ на: комментарий от HappySquirrel

>Итого - 6 запросов и никаких циклов. На 4K записей это будет примерно 50..300 msec - в зависимости от железа и сервера.

+1, тока 6 многовато, имхо оптимально 3 запроса, а если потратить 15 минут наверника и в один четырехэтажный запихнется, но один оптимизатор может неосилить.

>Этот горе-тестер, например, просто переписал с Java на SQL свою задачу. Это как на автомобиле ехать задним ходом. Ну не понял он - как работает SQL. Не слышал никогда про GROUP BY .. HAVING ..

зато какое резюме, куда нам "местечковым гениям" до такого профи :)

на самом деле что там наворотил в pl/sql не столь и важно - алгоритм где-то тот же ну и черт с ним (хотя вопрос как он умудрился тормознуть даже круче жава конечно провамочен). просто если бы этот "профи" хотя бы 100К записей первого запроса попробывал тащить в свою жава - то разница уже была бы на _порядок_, а если ранести апп сервер и субд то 2 порядка. тут разница в пару милисикунд pl/sql просто не имеет ни какого значения :)

Minotauros.

anonymous
()

Я бы еще попросил тарссировку события 10046 8-го уровня и сравнил куда время уходит.

anonymous
()
Ответ на: комментарий от anonymous

> Я бы еще попросил тарссировку события 10046 8-го уровня и сравнил куда время уходит.

А так разве неясно? Он умудряется на каждую запись внешнего цикла выполнить по крайней мере один запрос. Я уж не помню - сколько у него там записей во внешнем цикле, но видимо много :)

HappySquirrel
()
Ответ на: комментарий от anonymous

> тока 6 многовато, имхо оптимально 3 запроса, а если потратить 15 минут наверника и в один четырехэтажный запихнется, но один оптимизатор может неосилить.

Я просто не знаю Oracle в деталях. 6 сработает на любом современном SQL сервере. Ессно возможны оптимизации. Но меньше одного всяко - не получится :)

Был у меня в бытность работы в одном из банков сослуживец. Его единственная обязанность была в обслуживании одного SQL запроса размером 42KB. Эдакий UPDATE-переросток. Он считал баланс банка на Informix в течение пары суток. Вадик, отзовись, скажи им!

HappySquirrel
()
Ответ на: комментарий от HappySquirrel

дыбелизм, автор или не понимает для чего нужны java/plsql. Сравнивает внутрению работу с данными с внешней. Сила pl/sql в том что умеет работать напрямую с ядром sql и лапатить терабайты, любой application server сляжет от такой работы. Могу опровергнуть любой тест. автору незачёт, все кто его поддержал - учить матчасть

anonymous
()

Да блин, чувак похоже - офигезный спец во всем!

>Tools Ada, ALGOL, ALGOL-W, APL, Business Objects, C, C++, Cadre/Teamwork, CASE*Dictionary, CASE*Generator, CICS, CMS-2M, COBOL, CORBA, DCL, DDP Assembler, DEC Datatrieve, DEC FMS, Designer/20000, Forth, FORTRAN, Hypercard, HyperTalk, IMS with DL/1, Ingres, Ingres 4GL, Ingres/Vision, Interleaf, Jovial, Kermit, Librarian, Lisp, Make, Microsoft Basic, Modula-2, MTASS-M, ODBC, OMTool, Oracle7, Oracle/RDB, Oracle*CASE, Oracle*Forms 4.0, Oracle*Reports 2.0, Pascal, Perl, PL/1, PL/SQL, Power Play, Prolog, r:Base 5000, RDB, SAIL, SCCS, Scheme, SDML/SGML, Shell Script, SNOBOL, Sperry Host-16, Sperry SSG, SPSS, SQL, SQL*Forms, SQL/Server, Sun's DevGuide, Sybase, Univac 1616 Assembler, VAX Document, Verdix Ada Development System, VSAM, XView (X-Windows), Yacc/Lex

Ximandr
()

а вот кто из спецов по ХП скажет что будет быстрее: хранилище метаданных ФС реализовано в базе данных (опустим зачем это и к чему), для поиска имён файлов используются регулярные выражения, имена файлов хранятся как

1. full pathname, для поиска используются обычные регулярные выражения в SQL запросе

2. file name + ссылка на директорию содержащую данный файл, поиск по регулярным выражениям производится путём склейки full pathname из имён директорий верхних уровней и имени самого файла и применения регулярного выражения к полному составному имени (в ХП)

первый вариант предельно прост, но неоправдано раздувает метаданные (такая вот денормализация для оптимизации) и объём базы данных, второй вариант сложнее и в реализации и вычислительно, но существенно уменьшает объём БД за счёт однократного хранения каждого имени

вопрос: при кол-ве записей от нескольких миллионов и больше, какой вариант будет быстрее и насколько?

filin ★★
()
Ответ на: комментарий от anonymous_IV

>А вообще я заметил что оракл настолько сложная вещь, что постигшие его специальные люди-ораклоиды ничего более осилить не в состоянии

А прикиньте, каково писать XML-парсер на PL/SQL для 7ки. Ибо быдломанагеры от Жабы шарахуются.

anonymous
()
Ответ на: комментарий от anonymous

>А прикиньте, каково писать XML-парсер на PL/SQL для 7ки. Ибо быдломанагеры от Жабы шарахуются.

ну видно какие манагеры такие и кодеры, через пару месяцев 9-ку перестанут супортить от старости, а тут клоуны быдло-кодят на версии которая релизнулась до появления жава :))))

anonymous
()

В тухес прикладной уровень - Java в Oracle и на сервере живёт.

А в Postgres и не только жаба...

anonymous
()
Ответ на: комментарий от anonymous_IV

>With two rules, it's easy to work out the four conditions that apply. For n rules, there are 2n predicate combinations that need to be analyzed and optimized. I'm daunted by the prospect, and don't see how a sizable collection of if-then-else business rules can be optimized into simple SELECTS.
------------------------------
аффтар полное ламо, даже студенты как то серьезней рассуждают ...


anonymous
()
Ответ на: комментарий от anonymous

адекватный автор снес мой коментарий :)

Minotaurus.

anonymous
()

> Let's see this benchmark.

Фи. "У меня много бизнесс-рулесов, и я не могу на них напридумывать SQL запросов, я лучше так, на жабе набыдлокодю". Это, блин, натурально, проблема американских программистов-за-деньги -- кодить надо быстро, пока заказчик не пердумал давать баппки, а что код получается говном никого не волнует, купите себе гигабайты памяти и будет вам счастье. И никому уже не интересно, что любая построчная обработка данных клиентом будет тормознее грамотных SQL запросов, которые просто отдадут клиенту результат, кроме некоторых исключительных случаев, когда, например, всё равно надо выбрать все строки и устроить им нетривиальную обработку.

Я помню какой ужасный код на PL/SQL получается, когда из сырых бинарных данных разбираются результаты звонков междугородней АТС (хранить сырые данные в базе надо было по условию задачи сверху). Выходом оказалось грузить сырые данные отдельно, обработанные перлом отдельно, скорость обработки сырых данных выросла раз в 5, учитывая дополнительную загрузку данных SQL*Loader. Это я к тому, что бывают неподходящие к PL/SQL задачи, когда действительно клиентское приложение может выиграть, но уж очень это не похоже что описывает автор, который похоже просто стремится успеть срубить бабла, и написать статейку, которая его оправдает.

Casus ★★★★★
()
Вы не можете добавлять комментарии в эту тему. Тема перемещена в архив.