Возможна ли работа работа с базой данных на С++ без SQL запросов?

238
15 декабря 2017, 03:27

Есть некая СУБД (думаю не важно какая) и при этом достаточно большого объема - миллионы записей в разных таблицах, у которой по некоторым причинам запросы выполняются неимоверно долго - от 2х часов. Есть ли возможность работы с БД прямо на сервере через высоко оптимизированное С++ приложение которое будет брать данные не по SQL запросу а прямо с дисков и формировать их на вывод? например как временную таблицу для вывода клиенту.

P.S. Да я натыкался на статьи которые это как раз и обсуждают, но конкретно примеров я не смог найти

Answer 1

Могу сказать пару слов про PostgreSQL, но общий посыл будет одинаковый для всех СУБД и уже изложен в комментариях к вопросу.

Механизм extensions в PostgreSQL позволяет написать компилируемый код и вмешиваться в работу СУБД. Не вижу причин, мешающих из extension реализовать более низкоуровневое чтение данных требуемым способом. extension в postgresql может очень многое сделать.

Для общения с приложением чуток SQL при этом скорей всего останется - но просто потому, что реализовать передачу данных на клиент проще через SQL, в частности в формате вызова хранимой процедуры:

select * from my_extension_function_read_data();

Не думайте, однако, что это будет просто. Некоторый объём SQL-запросов есть даже в ядре этой СУБД - например материализованные представления строятся на самом деле с использованием SQL. Через SQL же, сюрприз, сейчас реализованы проверки foreign key.

Если вы захотите использовать индекс - то будьте добры сходить в pg_catalog, найти там самостоятельно подходящий индекс и с использованием access method API к нему обратиться подходящим (!) способом - я имею в виду, что есть несколько возможных способов использовать один и тот же индекс и не для всех access method все эти способы реализованы. Если вы захотите сделать сортировку - будьте добры её делать самостоятельно или разбираться, как она сделана в штатном executor, в том числе что делать если у вас данных больше чем памяти. А уж если хотите что-то переджойнить или аггрегировать...

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

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

Основной вопрос и ответ, впрочем, в другом. Если вы знаете, как эффективно получать требуемые данные - то значительно разумнее не хардкодить механику планировщика и переизобретать executor, а разобраться, как попросить вашу СУБД использовать именно такой план запроса и понять почему обычно планировщик от этого плана отказывается. Универсальный планировщик запросов работает на статистике, математике и чёрной магии - и вполне может ошибаться по разным причинам. Или же ошибаться можете как раз вы в своих предположениях, а планировщик выбрал более подходящий план. Или же СУБД настроена странно (тот же postgresql из коробки поставляется с конфигом чтобы запуститься и никому не мешать, а не эффективно использовать имеющееся железо). Или же вы просто написали что-нибудь странное с точки зрения планировщика в запросе, что тот не понимает как переписать. Например, не все планировщики понимают, что where id + 5 = 10 эквивалентно where id = 10 + 5 - в результате первый запрос будет делать полный просмотр таблицы, а второй - сможет использовать индекс.

READ ALSO
Предупреждение C4239: nonstandard extension used

Предупреждение C4239: nonstandard extension used

Почему возникает предупреждение

188
Как задать граф в языке C++ (Призма Мебиуса)

Как задать граф в языке C++ (Призма Мебиуса)

Здравствуйте, как задать такой граф в языке C++?

169
Что такое компаратор?

Что такое компаратор?

В вопросе Поиск самой длинной строки я увидел слово компаратор, но поскольку я мало понимаю в программировании, то я не знаю что это может...

216
Unit test для синглтона

Unit test для синглтона

Всем привет! Понимаю, что сам вопрос звучит довольно глупо, но столкнулся с такой задачейНужно сделать Юнит тесты для класса являющимся синглтоном,...

158