Re[45]: EntityFramework - тормоз
От: Evgeny.Panasyuk Россия  
Дата: 19.04.15 19:57
Оценка:
Здравствуйте, Ночной Смотрящий, Вы писали:

НС>>>Нет, не используется. Используется генерация кода.

EP>>Во время сборки/компиляции или в runtime? (bytecode emit?)
НС>Тулой во время сборки, без тулы при первом использовании в рантайме.

1. В прошлый раз ты говорил что "во время сборки" было в BLToolkit, да и то как выяснилось не в нём самом, а в сторонней утилите. Причём ЕМНИП BLToolkit'у на замену пришла Linq2DB — эта утилита работает и для него? Или есть аналог?
2. Это же по сути мета-программирование времени сборки, своего рода обработка DSL до runtime для ускорения LINQ — собственно с этого и началась подветка

EP>>То есть от LINQ практически нулевой overhead?

НС>Не нулевой, но довольно маленький.

Если для mapping'а генерируется байткод (который может быть настолько быстрым, насколько позволяет платформа) и используется скомпилированный запрос — то откуда вообще взяться overhead'у?

EP>> Или ты всё же про скомпилированные запросы?

НС>Конкретно linq2db компиляцию запросов даже в рантайме кеширует.

То есть не нужно специально вызывать компиляцию запроса? (а то тут выше говорили что для динамически-композируемых запросов это как-то неудобно)

НС>Проблема там только одна — для получения хеша запроса приходится обходить дерево. Это на самом деле довольно быстро (не в EF, так индусы наиндусячили) — никакого рефлекшена при обходе нет, там обычная AST в памяти максимум на сотню-другую узлов. Но да, какой то процент на куче мелких запросов отыграть можно, если МС соблаговолит дать возможность сделать это быстрее, подпилив компилятор шарпа.


Этот AST по идее должен лежать в памяти достаточно компактно, и соответственно должен обходится быстро.
Если обход долгий из-за кривого API, то можно попробовать сделать свой обход через unsafe Но нужно знать внутреннюю структуру, либо тогда делать reverse engineering
Re[33]: EntityFramework - тормоз
От: gandjustas Россия http://blog.gandjustas.ru/
Дата: 19.04.15 20:06
Оценка: 2 (1)
Здравствуйте, AK107, Вы писали:

AK>вы могли бы привести реальные тесты/замеры/цифры затрат на linq генерацию, чтобы говорить уже не об абстрактных вещах которые уже по пятому разу интерпретируются в нужную сторону от микросекунд до миллисекунд? ну чтобы спор стал предметным и можно было "тыкать носом"

Вот тут видео, там тест показываю http://gandjustas.blogspot.ru/2014/09/asp.net-linq-ef-sql-server-performance.html
Конкретное место — https://youtu.be/I2cNUUC3tiI?t=29m59s
Re[36]: EntityFramework - тормоз
От: gandjustas Россия http://blog.gandjustas.ru/
Дата: 19.04.15 20:11
Оценка: +2
Здравствуйте, alex_public, Вы писали:

_>Ну и если говорить о чтение, то откуда там обязательно IQueryable? ) Скорее User dbGetUser(int id); и vector<User> dbGetUsers(); или что-то подобное. )


Если ты возвращаешь объект, то должен поднять все его поля из базы, это значит нет проекций и все индексы идут нафиг, повышеная нагрузка на сеть и затраты на материализацию. И это все даже если тебе просто имя пользователя вывести нужно. А если у тебя 100500 методов под каждый запрос, то поддерживать их — ад, банальное добавление постраничной разбивки и сортировки в dbGetUsers требует правки кучи мест.

Вот ты сам и показал зачем IQueryable нужен практически везде.
Re[36]: EntityFramework - тормоз
От: Mamut Швеция http://dmitriid.com
Дата: 19.04.15 20:20
Оценка: +1
M>>Не может. Потому что несмотря на заточенность «движка», приложение почти сразу будет использовать специфические для выбранной БД запросы.

_>И это вызовет привязку к конкретной БД как раз только в случае отсутствия слоя абстракции БД. А в нормальных местах работа идёт именно через него + имеем набор реализаций этого слоя под каждую конкретную БД, где и используются те самые специфические запросы.


«Нормальная» асбтракция и «набор реализаций этого слоя» — это миф. Его в природе не бывает. То есть он бывает, конечно (типа sql alchemy), но на практике рано или поздно все начинают лопатить БД-зависимые запросы.

Странно, что ты этого не понимаешь

Любой «независимый от баз данных» слой сможет покрыть только общий для всех баз данных функционал + некоторое количество хаков для некоторых вещей. Ну типа генерация последовательностей для баз данных, где последовательностей не существует. Или грязные хаки для windowing functions.

Как только нужна внятная быстрая функциональность за пределами банальных джойнов или запросы, которые учитывают порядок индексов (что важно для, например, mysql'я), то вся «независимая прослойка» летит к черту.


ЗЫ. Чтобы вообще разжевать и в рот положить.

Если база данных не поддерживает PostgreSQL'овское generate_series, то тебе никакая магическая абстракция не поможет. И приложение будет моментально привязано к PostgreSQL как только это понадобится (а оно понадобится)


dmitriid.comGitHubLinkedIn
Re[46]: EntityFramework - тормоз
От: Ночной Смотрящий Россия  
Дата: 19.04.15 20:38
Оценка:
Здравствуйте, Evgeny.Panasyuk, Вы писали:

EP>1. В прошлый раз ты говорил что "во время сборки" было в BLToolkit, да и то как выяснилось не в нём самом, а в сторонней утилите.


И что? Я никогда и не утверждал, что "в нем самом". Тебе шашечки или ехать?

EP> Причём ЕМНИП BLToolkit'у на замену пришла Linq2DB — эта утилита работает и для него? Или есть аналог?


Я этот вопрос не изучал ибо мне без надобности.

EP>Если для mapping'а генерируется байткод (который может быть настолько быстрым, насколько позволяет платформа) и используется скомпилированный запрос — то откуда вообще взяться overhead'у?


Построить запрос это дорого, в некоторых провайдерах — очень дорого. linq2db поэтому построение запроса кеширует. К сожалению, компилятор шарпа генерирует код, который строит дерево при каждом исполнении метода, т.е. дерево каждый раз разное. Из-за этого, чтобы сравнить запросы, приходится обходить это дерево и вычислять хеш. Это тоже довольно быстро, но уже не мгновенно.

НС>>Конкретно linq2db компиляцию запросов даже в рантайме кеширует.

EP>То есть не нужно специально вызывать компиляцию запроса?

Нет, не нужно. CompiledQuery, в отличие от того же EF, позволяет сэкономить сильно меньше — как раз то самое вычисление хеша.

EP> (а то тут выше говорили что для динамически-композируемых запросов это как-то неудобно)


Это просто невозможно. Но в такой ситуации текущий вариант в принципе почти самое быстрое что можно придумать.

EP>Этот AST по идее должен лежать в памяти достаточно компактно, и соответственно должен обходится быстро.


Так и есть.

EP>, то можно попробовать сделать свой обход через unsafe Но нужно знать внутреннюю структуру, либо тогда делать reverse engineering


unsafe не спасет. Единственное в чем он дает существенный выигрышь на практике — отключение проверок границ массивов. Но в Expression Tree массивов не сказать чтобы много.
Re[39]: EntityFramework - тормоз
От: Evgeny.Panasyuk Россия  
Дата: 19.04.15 20:38
Оценка:
Здравствуйте, gandjustas, Вы писали:

EP>>В buffer pool ведь сидят страницы, в которых находятся целые строки таблиц, так? Тогда:

EP>>1. Закэшированный результат запроса скорей всего будет занимать меньше памяти чем "эквивалентный" набор страниц для повторного запроса, так как в нём будет меньше столбцов и строк — только самое необходимое. А следовательно будет больше свободной памяти, которую можно использовать под другие страницы, или другие кэши запросов.
G>Интересно как ты это посчитал.

Вариант 1. Запрос с агрегированием и группировкой, да ещё и не по всем столбцам — результат очевидно меньше чем исходные данные.
Вариант 2. Запрос с фильтрацией, с выводом всех столбцов. Без кэша результата, даже если загружены в память только минимально необходимые страницы, то они всё равно будут содержать неиспользуемые строки, помимо этого в памяти будут сидеть страницы соответствующего индекса.
Вариант 3. Запрос выводит все строки*столбцы, но в определённом порядке. В этом случае память также будет расходоваться под индекс, а в случае готового результата — нет, не говоря уже о том что линейный обход памяти на порядок (а бывает и на порядки) эффективней случайного.

G>Даже если в программе банальный CRUDL, то к каждой таблице идет минимум два запроса — на получение списка и на чтение одной строки по ключу. То есть в кеше будет занимать БОЛЬШЕ данных чем buffer pool. В реальном приложении, с джоинами будет еще больше данных в кеше. А если список достаточно большой и запросы равновероятны, то от кеша вообще толку нет, так как hit ratio будет слишком низкий.


А я не говорил что нужно кэшировать все запросы.
Хотя можно представить случаи где и автоматический кэш будет эффективен

EP>>2. Даже если все необходимые страницы в памяти, то "эквивалетная" закэшированному запросу операция может занять намного больше времени — так как требуется обработать больше данных из random'ных участков памяти.

G>Тытоже не понимаешь как базы работают?

А ты перестал пить коньяк по утрам?

G>Когда данные уж в ОП, то там различия минимальные, доли миллисекунд.


Элементарный пример — есть таблица в 30 гигабайт, для неё нужно сделать агрегирование с результатом в одну строчку. Угадай что будет быстрее — закэшированный результат или полное вычисление?
Пример конечно экстремальный, но поинт простой — готовый результат может быть в разы, а то и на порядки быстрее чем сырые данные. Причём не теряет актуальность даже в если до DB существенное latency — например в том случае если запросов много.
Re[40]: EntityFramework - тормоз
От: gandjustas Россия http://blog.gandjustas.ru/
Дата: 19.04.15 21:13
Оценка: +1 -1
Здравствуйте, Evgeny.Panasyuk, Вы писали:

EP>Здравствуйте, gandjustas, Вы писали:


EP>>>В buffer pool ведь сидят страницы, в которых находятся целые строки таблиц, так? Тогда:

EP>>>1. Закэшированный результат запроса скорей всего будет занимать меньше памяти чем "эквивалентный" набор страниц для повторного запроса, так как в нём будет меньше столбцов и строк — только самое необходимое. А следовательно будет больше свободной памяти, которую можно использовать под другие страницы, или другие кэши запросов.
G>>Интересно как ты это посчитал.

EP>Вариант 1. Запрос с агрегированием и группировкой, да ещё и не по всем столбцам — результат очевидно меньше чем исходные данные.

Да, только в случае агрегации актуально, но это если таблица не используется в других запросах.

EP>Вариант 2. Запрос с фильтрацией, с выводом всех столбцов. Без кэша результата, даже если загружены в память только минимально необходимые страницы, то они всё равно будут содержать неиспользуемые строки, помимо этого в памяти будут сидеть страницы соответствующего индекса.

EP>Вариант 3. Запрос выводит все строки*столбцы, но в определённом порядке. В этом случае память также будет расходоваться под индекс, а в случае готового результата — нет, не говоря уже о том что линейный обход памяти на порядок (а бывает и на порядки) эффективней случайного.
Ты точно знаешь как базы работают? Про покрывающие индексы не слышал?

G>>Даже если в программе банальный CRUDL, то к каждой таблице идет минимум два запроса — на получение списка и на чтение одной строки по ключу. То есть в кеше будет занимать БОЛЬШЕ данных чем buffer pool. В реальном приложении, с джоинами будет еще больше данных в кеше. А если список достаточно большой и запросы равновероятны, то от кеша вообще толку нет, так как hit ratio будет слишком низкий.


EP>А я не говорил что нужно кэшировать все запросы.

А вот a_alex_public_ утверждал что автокеш в базе — хорошее решение.

EP>Хотя можно представить случаи где и автоматический кэш будет эффективен

Представить вообще можно что угодно, а вот на практике встретить не всегда.

EP>>>2. Даже если все необходимые страницы в памяти, то "эквивалетная" закэшированному запросу операция может занять намного больше времени — так как требуется обработать больше данных из random'ных участков памяти.

G>>Тытоже не понимаешь как базы работают?
EP>А ты перестал пить коньяк по утрам?
Ответить нечего?

G>>Когда данные уж в ОП, то там различия минимальные, доли миллисекунд.


EP>Элементарный пример — есть таблица в 30 гигабайт, для неё нужно сделать агрегирование с результатом в одну строчку. Угадай что будет быстрее — закэшированный результат или полное вычисление?

Индексированное представление, а кэш не нужен.

EP>Пример конечно экстремальный, но поинт простой — готовый результат может быть в разы, а то и на порядки быстрее чем сырые данные. Причём не теряет актуальность даже в если до DB существенное latency — например в том случае если запросов много.

Походу ты действительно не знаешь как работают базы данных. Не продолжай пожалуйста.
Re[37]: EntityFramework - тормоз
От: alex_public  
Дата: 19.04.15 21:14
Оценка:
Здравствуйте, Ночной Смотрящий, Вы писали:

НС>Нет, не понимаю. Чтобы хранить граф в РСУБД придется придумать для него реляционное представление. Если же решать задачу в лоб, просто преобразуя связи в FK, то, с хорошей вероятностью, тормоза обеспечены.


О том и речь — реляционная модель подходит не всегда.

НС>Да просто указываешь его в качестве типа свойства класса модели и все. Плюс там какие то требования к этому классу есть, я сейчас по памяти точно не помню. Модель данных, о которой я говорил это прежде всего связи. А маппинг между типом БД и типом CLR это мелочь, которую умеет любой приличный ORM.


Ну меня больше интересует не конкретный синтаксис, а изменит ли это накладные расходы по отношению к варианту с просто int'ом.

НС>Не абстракция, а банальная функция. Нет нужды ее выносить в отдельный слой. На практике обычно такое пишется прям по месту, а если вдруг понадобилось где то еще, то делается один из самых примитивных рефакторингов — extract method. Причем соверешнно пофигу, если там линк, нет его, им есть ли там вообще хоть что то напоминающее БД.


Ну естественно подразумевается, что и весь остальной доступ к БД реализован через подобные функции. Ну и собственно сделав этот самый extract method для всех упоминаний БД в приложение, ты и получишь тот самый слой абстракции. А дальше возможно сделать несколько альтернативных реализаций, в зависимости от используемого движка для хранения данных.

НС>Во во. Об этом я и говорю — плодим кучу методов, внутри которых перекладывание из пустого в порожнее. И что особо радует глаз, так это то что 90% таких методов вызываются ровно в 1 месте. Я уж не говорю про веселье под названием User — то ли мы из БД все сразу тянем, то ли этот самый User в полуинициализироыванном состоянии. А потом веселый парень передает этот User куда нибудь, где кто то ждет те поля, которые на самом деле незаполнены, и привет странные и трудно вылавливаемые глюки. И это, замечу, не несуществующие ситуации типа сложения рублей с килограммами, а самая что ни на есть скучная рутина.

НС>Вобщем, стрелять. Ставить перед пушкой и стрелять.

Это всё общие слова ни о чём. На практике большинство известных движков реализовано именно с помощью подобного слоя абстракции бд и отлично работают.

_>> Однако если мы говорим о конкретном приложение с конкретной БД (не СУБД, а именно таблицами и т.п.), то какие могут быть проблемы в написание оптимального слоя абстракции?

НС>Ненужная и вредная работа и раздутый на ровном месте код.

Т.е. удобный API в терминах приложения и отсутствие никчемных накладных расходов — это ненужная и вредная работа? ) Понятно, понятно. )))
Re[39]: EntityFramework - тормоз
От: alex_public  
Дата: 19.04.15 21:16
Оценка:
Здравствуйте, Ночной Смотрящий, Вы писали:

_>>Прочти внимательнее, на что я отвечал. Там же чётко написано "это уже речь не про обсуждаемый здесь linq к БД, а про просто linq, который ещё более печален."

НС>Ну то есть ты признаешься что решил заняться демагогией и перевести тему?

Почему перевести? ) Я и старую тему не бросил. Однако это не мешает пообсуждать в ответвление темы соседний вопрос.
Re[37]: EntityFramework - тормоз
От: alex_public  
Дата: 19.04.15 21:29
Оценка: :)
Здравствуйте, IT, Вы писали:

IT>Т.е. ты можешь совершенно точно сказать где именно у linq критические в плане производительности места и как с этим можно бороться?


Конечно. Только вот бороться с этим весьма проблематично, т.к. узкое место заложено в саму базовую архитектуру. Более того, если мы взглянем на то, как в других языках сумели решить данную задачу без подобных накладных расходов, то увидим, что там интенсивно используется метапрограммирование, которое недоступно в C#. Хотя конечно можно попробовать реализовать подобные оптимизации через рефлексию, но опять же это всё будет в рантайме и соответственно компилятор не сможет заинлайнить такой код. В общем если оставаться в рамках C# и требуется получить максимальную производительность, то ничего кроме использование тупых for'ов не видно. Разве что использовать какую-то внешнюю кодогенерацию, но это же уже будет не совсем C#. )))
Re[35]: EntityFramework - тормоз
От: alex_public  
Дата: 19.04.15 21:36
Оценка:
Здравствуйте, AK107, Вы писали:

AK>ну вообще здесь есть сравнение, но данные устаревшие. разница между plain sql и bltoolkit в любом случае не драматична, да и не должна быть таковой в виду сетевого ввода/вывода, даже если в СУБД все закэшировано по самый край


Интересные цифры. Жаль что устаревшие. Хотелось бы увидеть их современный аналог.

Да, и разница более чем драматическая. Там автор гордится тем, что удалось добиться заторможенности не в 10 раз, а всего то раза в 2. А лично для меня и такая цифра кажется дикостью. Кстати, а в этой темке сторонники linq говорили о заторможенности в пределах максимум 1-10%.
Re[43]: EntityFramework - тормоз
От: alex_public  
Дата: 19.04.15 21:43
Оценка:
Здравствуйте, Ночной Смотрящий, Вы писали:

НС>А твой вопрос, без конкретных запросов, БД, железа и т.п. — тоже ни о чем. Интересно значение в конкретной ситуации — напиши и прогони тест сам. Я за тебя это сделать не в состоянии. А на моих данных — я сказал.


Никто и не просит точные цифры. Но по порядку величины (хотя бы речь о микросекундах или миллисекундах) вполне можно сообщить, т.к. это не будет зависеть от БД или железа. Максимум от сложности запроса. Ну соответственно можно указать пределы (для простого запроса и для сложного).

НС>И могу тебе другое сказать — переписывание реальных приложений с текстовых запросов и ХП на linq мне приходилось делать несколько раз. И всегда после переписывания приложение начинало работать быстрее, от десятков процентов до разов. Хочешь верь, а хочешь нет.


Настоящий специалист и на Питоне обгонит говнокодера на Ассемблере. ))) От этого Питон не станет быстрым языком. )
Re[41]: EntityFramework - тормоз
От: alex_public  
Дата: 19.04.15 21:52
Оценка:
Здравствуйте, gandjustas, Вы писали:

G>С чего ты взял? Как раз большая часть разработчиков работает в конторах, которые специализируются на софте.


Ну ну) Посчитай какой процент от всего бизнеса (а IT отдел сейчас есть считай в любой приличной компании) занимают софтверные вендоры. )))

_>>А я тебе уже 10 раз ответил, что двумя руками за подобный тул для автоматизации. Речь была исключительно о том, что конкретная реализация по имени linq очень далека от идеала.

G>Так другой нет. Да и с Linq проблем не много, поэтому не надо чинить что не сломано. В других языках даже близко подобного нет.

В C# может и нет, а в других языках есть. Что тебе тут и продемонстрировали. Просто ты этого упорно не хочешь признавать.
Re[39]: EntityFramework - тормоз
От: alex_public  
Дата: 19.04.15 22:05
Оценка:
Здравствуйте, gandjustas, Вы писали:

_>>Это ты похоже бредишь, если считаешь что размер кэша и основной памяти должен быть одинаковым. Даже если не можешь провести аналогию с классическими кэш системами, то хотя бы просто взглянул на дефолтное значение параметра размера кэша в обсуждаемых СУБД.

G>А с чего ты взял что я так считаю?

Потому что говоришь о притеснение кэшем памяти отведённой под таблицы. ))) В то время как на практике это совсем разные числа.

G>Это при условии что один и тот же запрос приходит Ты же понимаешь что в реальности так не бывает. Тебе прилетит 1000 разных запоров, а только 1001 будет повторять первый. При этом кеш первого уже вытеснен, а ОП для buffer pool стало меньше ровно на размер кешей и внезапно нужные страницы не в памяти, и ты попадаешь на физическое чтение.

G>На маленькой базе этого не будет видно, а на большой — еще как.

G>Даже если кешировать на стороне приложения и иметь огромный объем памяти под кеш за пределами базы, то кешировать все запросы — крайне неэффективная стратегия (сам делал, знаю). А в базе, отбирая ресусры у buffer pool — вообще выглядит плохой шуткой. В лучшем случае выборочный кеш нужен, а в идеале за пределами БД.


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

_>>Повторюсь ещё раз: чем больше база, тем лучший будет эффект от включения кэша. Если тебе это не очевидно, то я даже не знаю о чём можно ещё говорить. )))

G>Архитектура баз данных говорит нам ровно обратное, о чем еще ты хочешь поговорить?
G>Или можешь объяснишь нам как кеш помогает уменьшить чтение с диска если приходят разные запросы?

Твоё понимание кэша справедливо только для случая запросов вида select * from ... where id=xxx; причём при условие, что у нас вероятность запросов с id=xxx имеет равномерное распределение. Я думаю ты сам понимаешь, что в реальных системах картина совсем другая.
Re[47]: EntityFramework - тормоз
От: Evgeny.Panasyuk Россия  
Дата: 19.04.15 22:11
Оценка:
Здравствуйте, Ночной Смотрящий, Вы писали:

EP>>Если для mapping'а генерируется байткод (который может быть настолько быстрым, насколько позволяет платформа) и используется скомпилированный запрос — то откуда вообще взяться overhead'у?

НС>Построить запрос это дорого, в некоторых провайдерах — очень дорого. linq2db поэтому построение запроса кеширует. К сожалению, компилятор шарпа генерирует код, который строит дерево при каждом исполнении метода, т.е. дерево каждый раз разное. Из-за этого, чтобы сравнить запросы, приходится обходить это дерево и вычислять хеш. Это тоже довольно быстро, но уже не мгновенно.

Это понятно, но если использовать Compiled Query, то есть без обхода дерева — то получается что совсем не будет overhead'а? Здорово

EP>>Этот AST по идее должен лежать в памяти достаточно компактно, и соответственно должен обходится быстро.

НС>Так и есть.
EP>>, то можно попробовать сделать свой обход через unsafe Но нужно знать внутреннюю структуру, либо тогда делать reverse engineering
НС>unsafe не спасет. Единственное в чем он дает существенный выигрышь на практике — отключение проверок границ массивов. Но в Expression Tree массивов не сказать чтобы много.

Там наверняка какой-нибудь visitor на виртуальных функциях, и скорей всего обход узлов в памяти не последовательный, что медленно.
Если сделать допущение, что у одного и того же запроса узлы в памяти располагаются последовательно, то можно обходить узлы по порядку — как они лежат в памяти. Плюс надо будет "нормализировать" указатели-дуги, чтобы они не зависели от начального адреса. Плюс отказ от виртуальных функций в пользу хардкорного инлайнинга и jump table. Думаю всё это даст прирост скорости в несколько раз, а то и на порядок (порядки — если супер-оптимистично).
Но это конечно жуткий low-level hack, требующий кучи тестов и version-specific кода.
Re[37]: EntityFramework - тормоз
От: alex_public  
Дата: 19.04.15 22:14
Оценка:
Здравствуйте, gandjustas, Вы писали:

G>Если ты возвращаешь объект, то должен поднять все его поля из базы, это значит нет проекций и все индексы идут нафиг, повышеная нагрузка на сеть и затраты на материализацию. И это все даже если тебе просто имя пользователя вывести нужно. А если у тебя 100500 методов под каждый запрос, то поддерживать их — ад, банальное добавление постраничной разбивки и сортировки в dbGetUsers требует правки кучи мест.


Это был просто пример, а не универсальное решение. Ещё раз повторюсь: сделать универсальное оптимальное решение невозможно. Однако сделать это для конкретной задачи и БД нет никаких проблем.

G>Вот ты сам и показал зачем IQueryable нужен практически везде.


А вот IQueryable — это как раз попытка сделать универсальное решение. Более менее конечно же работает, но естественно будет всегда хуже частных решений.

В этом собственно и смысл слоя абстракции БД — он свой в каждом приложение. Естественно всегда были попытки как-то это автоматизировать (так и родились ORM), но всё равно добиться полноценной замены написанного человеком не выходит.
Re[38]: EntityFramework - тормоз
От: IT Россия linq2db.com
Дата: 19.04.15 22:21
Оценка:
Здравствуйте, alex_public, Вы писали:

IT>>Т.е. ты можешь совершенно точно сказать где именно у linq критические в плане производительности места и как с этим можно бороться?

_>Конечно. Только вот бороться с этим весьма проблематично, т.к. узкое место заложено в саму базовую архитектуру.

Поясни, плиз.
Если нам не помогут, то мы тоже никого не пощадим.
Re[37]: EntityFramework - тормоз
От: alex_public  
Дата: 19.04.15 22:30
Оценка: -1 :))
Здравствуйте, Mamut, Вы писали:

M>Любой «независимый от баз данных» слой сможет покрыть только общий для всех баз данных функционал + некоторое количество хаков для некоторых вещей. Ну типа генерация последовательностей для баз данных, где последовательностей не существует. Или грязные хаки для windowing functions.


Безусловно движку, умеющему работать с разными СУБД, приходится ограничиваться пересечением функционала этих СУБД. Но на самом деле этого обычно вполне достаточно, т.к. во всех нормальных СУБД есть всё нужное. Там основная проблема скорее в другом — в разных СУБД эта функциональность может по разному подключаться.

M>Как только нужна внятная быстрая функциональность за пределами банальных джойнов или запросы, которые учитывают порядок индексов (что важно для, например, mysql'я), то вся «независимая прослойка» летит к черту.


Эммм, по нормальному за пределами слоя работы с БД никаких джойнов и т.п. не должно быть. )

M>Если база данных не поддерживает PostgreSQL'овское generate_series, то тебе никакая магическая абстракция не поможет. И приложение будет моментально привязано к PostgreSQL как только это понадобится (а оно понадобится)


Дааа, PostgreSQL вообще далеко ушёл. Сейчас то он уже умеет и с json работать, т.е. замахивается на область nosql и даже в небольшой степени на обработку деревьев. Такими темпами он может когда-нибудь выйти в однозначные лидеры и тогда можно будет спокойно затачиваться под него — вот будет счастье для авторов всяких движков. ))) Но пока до этого ещё далеко.
Re[41]: EntityFramework - тормоз
От: Evgeny.Panasyuk Россия  
Дата: 19.04.15 22:33
Оценка: +1
Здравствуйте, gandjustas, Вы писали:

EP>>>>В buffer pool ведь сидят страницы, в которых находятся целые строки таблиц, так? Тогда:

EP>>>>1. Закэшированный результат запроса скорей всего будет занимать меньше памяти чем "эквивалентный" набор страниц для повторного запроса, так как в нём будет меньше столбцов и строк — только самое необходимое. А следовательно будет больше свободной памяти, которую можно использовать под другие страницы, или другие кэши запросов.
G>>>Интересно как ты это посчитал.
EP>>Вариант 1. Запрос с агрегированием и группировкой, да ещё и не по всем столбцам — результат очевидно меньше чем исходные данные.
G>Да, только в случае агрегации актуально, но это если таблица не используется в других запросах.

Как видишь, "не всё так однозначно" (c) — используя кэш всё-таки можно увеличить "свободную память"

EP>>Вариант 2. Запрос с фильтрацией, с выводом всех столбцов. Без кэша результата, даже если загружены в память только минимально необходимые страницы, то они всё равно будут содержать неиспользуемые строки, помимо этого в памяти будут сидеть страницы соответствующего индекса.

EP>>Вариант 3. Запрос выводит все строки*столбцы, но в определённом порядке. В этом случае память также будет расходоваться под индекс, а в случае готового результата — нет, не говоря уже о том что линейный обход памяти на порядок (а бывает и на порядки) эффективней случайного.
G>Ты точно знаешь как базы работают? Про покрывающие индексы не слышал?

И чем они помогут в случае динамических фильтров и динамических предикатов?

EP>>Хотя можно представить случаи где и автоматический кэш будет эффективен

G>Представить вообще можно что угодно, а вот на практике встретить не всегда.

Кто-то встретит, кто-то нет — для этого есть настройки.

EP>>>>2. Даже если все необходимые страницы в памяти, то "эквивалетная" закэшированному запросу операция может занять намного больше времени — так как требуется обработать больше данных из random'ных участков памяти.

G>>>Тытоже не понимаешь как базы работают?
EP>>А ты перестал пить коньяк по утрам?
G>Ответить нечего?

Я уже писал ранее что с СУБД вообще не приходится работать. Это, тем не менее, не освобождает оппонента от необходимости аргументировать свою позицию

G>>>Когда данные уж в ОП, то там различия минимальные, доли миллисекунд.

EP>>Элементарный пример — есть таблица в 30 гигабайт, для неё нужно сделать агрегирование с результатом в одну строчку. Угадай что будет быстрее — закэшированный результат или полное вычисление?
G>Индексированное представление, а кэш не нужен.

Для динамических запросов, с динамическими формулами?

EP>>Пример конечно экстремальный, но поинт простой — готовый результат может быть в разы, а то и на порядки быстрее чем сырые данные. Причём не теряет актуальность даже в если до DB существенное latency — например в том случае если запросов много.

G>Походу ты действительно не знаешь как работают базы данных.

Аргументов как всегда не будет?

G>Не продолжай пожалуйста.


Давай, удачи, слив засчитан
Re[42]: EntityFramework - тормоз
От: gandjustas Россия http://blog.gandjustas.ru/
Дата: 20.04.15 00:00
Оценка:
Здравствуйте, alex_public, Вы писали:

_>Здравствуйте, gandjustas, Вы писали:


G>>С чего ты взял? Как раз большая часть разработчиков работает в конторах, которые специализируются на софте.


_>Ну ну) Посчитай какой процент от всего бизнеса (а IT отдел сейчас есть считай в любой приличной компании) занимают софтверные вендоры. )))

В деньгах? Огромный. Например в одном банке (не могу назвать в каком по причине NDA) своя разработка кушает не более 5% ИТ бюджета, а услуги внешних компаний — около 20%. Причем в баках реально большие расходы на ИТ, в остальных отраслях соотношение еще меньше.

_>>>А я тебе уже 10 раз ответил, что двумя руками за подобный тул для автоматизации. Речь была исключительно о том, что конкретная реализация по имени linq очень далека от идеала.

G>>Так другой нет. Да и с Linq проблем не много, поэтому не надо чинить что не сломано. В других языках даже близко подобного нет.
_>В C# может и нет, а в других языках есть. Что тебе тут и продемонстрировали. Просто ты этого упорно не хочешь признавать.
Это ты веришь что они есть. А я не увидел ничего близкого по функционалу по сравнению с тем, что было в моих приложениях.
Подождите ...
Wait...
Пока на собственное сообщение не было ответов, его можно удалить.