powered by simpleCommunicator - 2.0.56     © 2025 Programmizd 02
Целевая тема:
Создать новую тему:
Автор:
Закрыть
Цитировать
Форумы / SQLite [игнор отключен] [закрыт для гостей] / Ньюсфид для крупной соцсети. SQLite?
69 сообщений из 69, показаны все 3 страниц
Ньюсфид для крупной соцсети. SQLite?
    #36538206
pavlikkk
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
Задача такая. Надо сделать ньюсфид для проекта, в с ежедневной посещаемостью в несколько миллионов юзеров.
То есть для каждого пользователя логируются события, которые происходят с ним либо с его друзьями при взаимодействии с различными сущностями проекта, внешними приложениями итд. Примерно то же, что сделано vkontakte.ru, если посмотреть "новости друзей".

Сейчас реализация такая. Все события для каждого id хранятся в памяти, группировка и фильтарция делается вручную при отдаче (все это на С++). Вся база дампится на диск при выключении демона, загружается при старте.
Проблема в том, что сейчас в день набегает несколько Гб данных, и хранить дальше все в памяти уже невозможно. Можно сделать шардинг на несколько серверов, но это сопряжено с проблемами ("новости друзей"). Хочеться попробовать выжать еще из одного сервера.

Собсно, идея такая - в памяти держать тока активный контент (сделать какой-то lru-кеш по обращениям), а то, что вытеснятется - дампить в какое-то хранилище. Собсно - вопрос, что лучше использовать в качестве него?

Начал писать собственный движок, но все время гложет мысль, не изобретаю ли я велосипед:) Что думаете начет libmysqld или sqlite ? Опыта работы ни с тем, ни с другим у меня нет.

Насколько хорошо работают эти штуки на объемах в пару сотен гигов при простых insert и select по числовому id? Что еще посоветуете? В первую очередь интересует мнение уважаемого MGB:)
...
Рейтинг: 0 / 0
Ньюсфид для крупной соцсети. SQLite?
    #36538260
Siemargl
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Это просто не для эскулайта задача. Потому что серверов-генераторов станет несколько. Нужен сервер, а не либа.

Скорее mysql, и транзакции вам не нужны.
...
Рейтинг: 0 / 0
Ньюсфид для крупной соцсети. SQLite?
    #36538318
MBG
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
MBG
Гость
pavlikkkНасколько хорошо работают эти штуки на объемах в пару сотен гигов при простых insert и select по числовому id? Что еще посоветуете?

Зависит от структуры данных. Если говорить "в общем", то сотни миллионов записей эскулайт в одной таблице обрабатывает хорошо:
Тестирование SQLite 3.6.17-mobigroup.2 на больших таблицах
Это при индексах на числовые поля; при использовании строковых индексов возникнут проблемы:
Degradation of indexing speed in SQLite 3.6.20

Имхо в описанной задаче стоит обращаться к БД напрямую на чтение (распараллеливая операции чтения на множество потоков выполнения), а запись выполнять из одного потока пакетно, например, раз в 5 секунд. В памяти можно вообще ничего не хранить, кроме не сброшенных на диск данных (хинт: используя in-memory SQLite базу можно с удобствами с ними работать).

Размер БД обязательно зафиксировать "сверху"- например, разделяя данные по дням. Это и удобно (например, для бэкапа), и обеспечит стабильное время выполнения выборок.

P.S. Сам я только в линуксе работаю, и ядро отлично кэширует часто запрашиваемые страницы БД. Под виндоус, возможно, все будет далеко не столь радужно.

P.P.S. Стоит подумать о хранении сериализованных структур данных - они и сами по себе здорово уменьшают объем БД, и сжатие использовать можно (zlib-сжатие особенно - скорость распаковки настолько велика, что эффективнее читать/писать на диск именно сжатый контент, распаковывая "на лету").
...
Рейтинг: 0 / 0
Ньюсфид для крупной соцсети. SQLite?
    #36539338
pavlikkk
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
Структура данных у нас простая - грубо говоря, одно событие - это
struct event {
int user_id;
int delete_id; /*уникальный id, назначемый клиентом и используемый им для удаления*/
std::string attachment; /*строка произвольной длины, содержащая доп.инфу про событие.*/
/*... набор id для фильтрации и группировки*/
};

Надо выбирать по большому набору id (все друзья юзера). Еще события нужно уметь удалять уникальному id(например, юзер добавил фотку, потом удалил). События происходят в произвольном порядке, соответственно база как я понимаю будет не только большая, но и очень фрагментированая.

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

Я так понимаю что SQLite полностью лочит базу при вставке, соответственно все читающие треды в этот момент будут ждать, и сервер будет лагать с какой-то периодичностью. Для этого собственно я и собирался использовать свой кеш, чтоб большинство чтений происходило прямо из него, а с базой работал отдельный тред или группа тредов(один на запись и несколько на чтение). По крайней мере кеш ОС(FreeBSD 7.3) в таком случае нас не выручал, и когда начинал сбрасываться буфер на диск, чтение начинало жутко тормозить(на SATA винтах).

Про zlib-сжатие хорошая идея, я тоже думал его использовать:)
...
Рейтинг: 0 / 0
Ньюсфид для крупной соцсети. SQLite?
    #36539411
MBG
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
MBG
Гость
Да, при вставке база блокируется. Но пакетная вставка тысячи записей это время порядка 50 миллисекунд, вас это не должно волновать. А вставка 1000 записей раз в 5 секунд это под 100 миллионов записей в сутки, что превосходит на порядок указанные вами требования. Если же это делать раз в секунду, получается под миллиард записей в сутки без заметной блокировки базы - на таких масштабах скорее кластер оракл загнется, нежели эскулайт замедлится :-)

Кстати, вот еще цифры - открытие БД требует примерно 500 микросекунд, на десктопном кореквадро можно около 4000 http-запросов с обращением к БД выполнить, притом селектов может быть десятки и сотни для каждого HTTP-запроса, т.к. они выполняются чрезвычайно быстро (порядка миллиона средней сложности селектов из view в минуту).


Вот практический пример - одну бизнес-систему переносил с постгреса на эскулайт. Дело давно было, ОЗУ на сервере имелось 1 Гб, а база постгреса была более 20 Гб и жутко тормозила на построении квартальных отчетов по выборкам в 3-5 Гб, а при запуске двух отчетов параллельно сервер насмерть свопился. БД на эскулайте получилась 5 Гб и работала в 60 раз быстрее, причем легко обрабатывала несколько параллельных запросов. Вся хитрость в том, что постгрес не умеет с дисковыми данными работать и все тянет в кэш в ОЗУ, отсюда и уходит в своп. Скулайт же работает с данными на диске, считывая их постранично и не требуя большого количества ОЗУ (только на хранение результата, по большому счету).
...
Рейтинг: 0 / 0
Ньюсфид для крупной соцсети. SQLite?
    #36539518
pavlikkk
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
Звучит очень убедительно, уже почти начал делать на SQLite, как вы сказали:)
Еще одно небольшое сомнение - сейчас появляются системы, использующие для хранения данных просто кучу маленьких файлов(например, фейсбуковская cassandra). Мнение у людей такое:

'Если вы используете доп. прослойку для работы с данными, то у вас просто плохая файловая система (Ганс Райзер)'

Может, действительно поставить линукс с той же ReiserFS и обойтись вообще без БД? Типа, БД это пережиток времени, когда файловые системы были еще плохими типа виндовых нынешних:) По идее, ReiserFS - тоже использует B+ дерево для индексов, компрессию поддерживает..А сложные запросы и прочие фичи БД мне и не нужны, сам сделаю если надо, нам не сложные отчеты делать, а просто хренову тучу однотипных выборок/вставок.

Что скажете?
...
Рейтинг: 0 / 0
Ньюсфид для крупной соцсети. SQLite?
    #36539630
Siemargl
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
pavlikkk,

Я как раз подобную идею проверяю , только на NTFS.

В Вашем контексте производительность будет не супер =(
...
Рейтинг: 0 / 0
Ньюсфид для крупной соцсети. SQLite?
    #36539658
MBG
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
MBG
Гость
Скажу, что Ганс и многие другие несут чушь :-) Контрпример словам Ганса - оцените эффективность хранения в файлах записей длиной 1 байт. Чувствуете? Будет занято безумно много дискового пространства, кэш ФС "захлебнется", таблица размещения файлов в ФС - "взорвется". Потому утверждения, не учитывающие параметров задачи, есть злостный популизм. И более того - зачастую ФС raiser3/4 работает поверх софтового рэйда и lvm, что, если следовать логике Ганса, есть результат его собственного быдлокода, поскольку его ФС не поддерживает партишионирование и проч. :-)

Оценить, когда стоит хранить данные на диске, несложно. Размер блока ФС обычно 4-8 килобайт. Если запись данных занимает в разы больше места, ей самое место именно на диске. Иначе - используйте базы данных, ведь они умеют эффективно хранить именно небольшие записи, где небольшие - меньше или равно по размеру странице БД (те же 4-8 килобайт).

Следующий момент - СУБД предоставляют множество разных структур хранения и индексов. Например, в эскулайт есть b-tree индекс, r-tree, полнотекстовый. И вот тут-то обнаруживается серьезное различие с ФС.

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

Заметьте - выши ни слова не сказано о возможностях SQL, речь шла только о форматах хранения как таковых.
...
Рейтинг: 0 / 0
Ньюсфид для крупной соцсети. SQLite?
    #36539721
Siemargl
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
MBGСкажу, что Ганс и многие другие несут чушь :-) Контрпример словам Ганса - оцените эффективность хранения в файлах записей длиной 1 байт. Чувствуете? Будет занято безумно много дискового пространства, кэш ФС "захлебнется", таблица размещения файлов в ФС - "взорвется". Потому утверждения, не учитывающие параметров задачи, есть злостный популизм. И более того - зачастую ФС raiser3/4 работает поверх софтового рэйда и lvm, что, если следовать логике Ганса, есть результат его собственного быдлокода, поскольку его ФС не поддерживает партишионирование и проч. :-)

Это все элементарно обходится и решается.
MBG
Оценить, когда стоит хранить данные на диске, несложно. Размер блока ФС обычно 4-8 килобайт. Если запись данных занимает в разы больше места, ей самое место именно на диске. Иначе - используйте базы данных, ведь они умеют эффективно хранить именно небольшие записи, где небольшие - меньше или равно по размеру странице БД (те же 4-8 килобайт).

Есть достаточно эффективные приемы хранения мелких объектов в памяти. Это на два порядка быстрее СУБД.
А старые архивные группировать и сбрасывать или в файл или в СУБД.
MBG
Следующий момент - СУБД предоставляют множество разных структур хранения и индексов. Например, в эскулайт есть b-tree индекс, r-tree, полнотекстовый. И вот тут-то обнаруживается серьезное различие с ФС.

Тут да. Если нужно поддерживать несколько индексов поверх ФС, то это уже не так удобно.
В памяти - boost::hash_mulitindex.
...
Рейтинг: 0 / 0
Ньюсфид для крупной соцсети. SQLite?
    #36539879
MBG
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
MBG
Гость
Siemargl
Есть достаточно эффективные приемы хранения мелких объектов в памяти. Это на два порядка быстрее СУБД.
А старые архивные группировать и сбрасывать или в файл или в СУБД.


Не надо советовать другим то, что вы сами не пробовали. Ваш "рецепт" совершенно нежизнеспособен.

Во-первых, два порядка взяты "с потолка". Защита от одновременной модификации данных разными потоками для многих миллионов записей с помощью мьютексов приведет к низкой производительности из-за постоянных блокировок, для решения проблемы придется делать множество наборов данных с отдельным мьютексом для каждого и управлять ими. И производительность будет отнюдь не такая же, как для примера из учебника с 1000-й элементов и без конкурентного доступа. И попробуйте сравнить с prepared запросом к эскулайт БД. При условии нормальной ОС и ФС - к примеру, linux kernel 2.6.32 + ext3.

Во-вторых, нет способов, и тем более эффективных, хранить в ОЗУ много данных, т.к. объем ОЗУ сильно ограничен и много данных туда физически не помещается. А если вам все равно придется часть данных поднимать с диска, то все преимущества своих самопальных структур данных вы потеряете, да еще огребете кучу проблем с кодом синхронизации и проч.
...
Рейтинг: 0 / 0
Ньюсфид для крупной соцсети. SQLite?
    #36540009
Siemargl
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
MBG,

Давайте постановку задачи (с достаточным упрощением) и проверим порядок. Блокироваться в памяти быстрее, чем блокироваться в кэше БД и в блоках на диске.
Только реализации задачи на SQL с Вас.
...
Рейтинг: 0 / 0
Ньюсфид для крупной соцсети. SQLite?
    #36540194
MBG
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
MBG
Гость
SiemarglMBG,

Давайте постановку задачи (с достаточным упрощением) и проверим порядок. Блокироваться в памяти быстрее, чем блокироваться в кэше БД и в блоках на диске.
Только реализации задачи на SQL с Вас.

Например, вот такой тест:
Тестирование SQLite 3.6.17-mobigroup.2 на больших таблицах

У вас - с многопоточной модификацией in-memory структуры при добавлении по одной записи, с частотой 1000 записей в секунду, с поддержкой индексов по полям и композитного (как описано в статье).

У меня - добавление записей пакетное ежесекундно, число записей в "пакете" - 1000. Для измерения скорости запросов скриптик напишу и статью дополню.

Измеряем:
1. Коэффициент доступности в процентах. Например, 80% означает, что 80% времени данные доступны для выборки или что данные блокируются на 0,2 секунды ежесекундно.
2. Скорость выборки набора записей, удовлетворяющих условию (запрос по одному индексу и по композитному, как в статье). В SQL делаю count(*), чтобы избежать затрат времени на передачу извлеченных данных - т.е. измеряется только время непосредственно выборки.
...
Рейтинг: 0 / 0
Ньюсфид для крупной соцсети. SQLite?
    #36540870
Siemargl
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
У меня все готово. 1000 записей в секунду даже несерьезно как-то =)

И вставка и поиск занимает 5-10мс. И крохи памяти.
...
Рейтинг: 0 / 0
Ньюсфид для крупной соцсети. SQLite?
    #36540929
MBG
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
MBG
Гость
SiemarglУ меня все готово. 1000 записей в секунду даже несерьезно как-то =)

И вставка и поиск занимает 5-10мс. И крохи памяти.

Показывайте код и результаты тестов. Интересно мне, как вы b-tree с композитным индексом реализовали для многопоточного окружения.

10 мс - это какая выборка? Сколько времени занимают выборки вида:

Код: plaintext
select count(*) from facts where a1= 2  and a2= 2  and a3= 2  and a4= 2 ;

с простым и композитным индексами?

Насчет крох памяти - по какому алгоритму выполняете перестройку индексного дерева?

Далее, если вставка записи занимает 5 миллисекунд, то в секунду удастся вставить лишь 200 записей. Про какое время вы говорите?
...
Рейтинг: 0 / 0
Ньюсфид для крупной соцсети. SQLite?
    #36540990
Siemargl
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
MBGSiemarglУ меня все готово. 1000 записей в секунду даже несерьезно как-то =)

И вставка и поиск занимает 5-10мс. И крохи памяти.

Показывайте код и результаты тестов. Интересно мне, как вы b-tree с композитным индексом реализовали для многопоточного окружения.

10 мс - это какая выборка? Сколько времени занимают выборки вида:

Код: plaintext
select count(*) from facts where a1= 2  and a2= 2  and a3= 2  and a4= 2 ;

с простым и композитным индексами?

Насчет крох памяти - по какому алгоритму выполняете перестройку индексного дерева?

Далее, если вставка записи занимает 5 миллисекунд, то в секунду удастся вставить лишь 200 записей. Про какое время вы говорите?
Как и говорил, boost::multi_index_contaiter<>. Лочим перед вставкой.

6-10мс выполняются суммарно два запроса
Код: plaintext
select count(*) from facts where a1= 2 ; select count(*) from facts where a1= 2  and a2= 2  and a3= 2  and a4= 2 ;

Вставка 1000 записей (само собой с индексами) занимает 3-5мс.
...
Рейтинг: 0 / 0
Ньюсфид для крупной соцсети. SQLite?
    #36540992
Siemargl
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Как будете готовы, пришлю .exe - 15кБайт - покрутите на своей машине.
...
Рейтинг: 0 / 0
Ньюсфид для крупной соцсети. SQLite?
    #36540996
MBG
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
MBG
Гость
SiemarglКак будете готовы, пришлю .exe - 15кБайт - покрутите на своей машине.

На кой мне .exe? Я виндоус видел последний раз пару лет назад и то в офисе у заказчика :-)
...
Рейтинг: 0 / 0
Ньюсфид для крупной соцсети. SQLite?
    #36541008
MBG
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
MBG
Гость
Siemargl
Как и говорил, boost::multi_index_contaiter<>. Лочим перед вставкой.

6-10мс выполняются суммарно два запроса
Код: plaintext
select count(*) from facts where a1= 2 ; select count(*) from facts where a1= 2  and a2= 2  and a3= 2  and a4= 2 ;

Вставка 1000 записей (само собой с индексами) занимает 3-5мс.

Так, вопрос по тестовому окружению. Сколько памяти у вас на машине? Сколько памяти занимают 100 миллионов записей с индексами? Плюс какой процессор. Насчет ОС уже все понятно - виндоус.

По этим двум запросам, пожалуйста, по отдельности время назовите, я их не зря в своих тестах разделил.
...
Рейтинг: 0 / 0
Ньюсфид для крупной соцсети. SQLite?
    #36541011
Siemargl
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Ну дык засунете в Wine - всего пяток функций из WinAPI - потянет.

( Жаль только пароли стырить не удастся Ж-< )

Кстати как на энтом форуме сворачивать код в + ??
...
Рейтинг: 0 / 0
Ньюсфид для крупной соцсети. SQLite?
    #36541023
Siemargl
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Памяти 1М объектов занял 100Мб.
Core t7200 2GHz.

10М лень создавать - долго секунд ждать по вашему алгоритму )

А 6мс поиска на 2 делить? И так точности нету. На наносекунды тоже не перейдешь - контекст свитчи больше займут.

Надо больше объемов итд. Как определитесь с базовой скоростью на эскулайте - привяжемся к новым количествам.
...
Рейтинг: 0 / 0
Ньюсфид для крупной соцсети. SQLite?
    #36541032
White Owl
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
SiemarglКстати как на энтом форуме сворачивать код в + ??
Нажми чтобы узнать...волшебное слово spoiler
...
Рейтинг: 0 / 0
Ньюсфид для крупной соцсети. SQLite?
    #36541051
Siemargl
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
White Owl, спс.

Куски кода, о чем речь.

Код: plaintext
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.
27.
28.
29.
30.
31.
32.
33.
34.
35.
36.
37.
38.
39.
40.
41.
42.
43.
44.
45.
46.
47.
48.
49.
50.
51.
52.
53.
54.
struct fact_stru
{
	int m_id;
	int m_a1;
	int m_a2;
	int m_a3;
	int m_a4;
	bool operator<(const fact_stru& e )const;
	
};

typedef multi_index_container<
  fact_stru,
  indexed_by<
    // sort by employee::operator less
    ordered_non_unique<identity<fact_stru> >,
    
    // sort by a1..a4
    ordered_non_unique<member<fact_stru,int,&fact_stru::m_a1> >,
	ordered_non_unique<member<fact_stru,int,&fact_stru::m_a2> >,
	ordered_non_unique<member<fact_stru,int,&fact_stru::m_a3> >,
	ordered_non_unique<member<fact_stru,int,&fact_stru::m_a4> >
  > 
> fact_set;

fact_set	db;
.....

bool insert1000()
{
	int count =  1000 ;
	for (;count >  0 ; count--)
	{
		fact_stru *fact = new fact_stru;
		fact->m_id = getFactId();
		fact->m_a1 =  18  * rand()/ RAND_MAX;
		fact->m_a2 =  18  * rand()/ RAND_MAX;
		fact->m_a3 =  18  * rand()/ RAND_MAX;
		fact->m_a4 =  18  * rand()/ RAND_MAX;
		db.insert(*fact);
		if (fact->m_id %  10000  ==  0 ) cout << "\n2:Inserted: " << fact->m_id << endl;
		if (fact->m_id >  1000000 ) return true; // stop all
	}
	return false;
}

void	threadInsert(LPVOID)
	do {
		// start run
		EnterCriticalSection(bufferCritSect);
....
		bool stop = insert1000();
....



Еще надо на утечку памяти проверить, только заметил =)
...
Рейтинг: 0 / 0
Ньюсфид для крупной соцсети. SQLite?
    #36541057
MBG
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
MBG
Гость
SiemarglПамяти 1М объектов занял 100Мб.
Core t7200 2GHz.

10М лень создавать - долго секунд ждать по вашему алгоритму )

Алгоритм дает очень удобное распределение. И 10М - тоже мало, берите 100М.

Siemargl
А 6мс поиска на 2 делить? И так точности нету. На наносекунды тоже не перейдешь - контекст свитчи больше займут.


Вы б еще на 1 записи тестировали :-) У вас мс - это миллисекунды?..

Siemargl
Надо больше объемов итд. Как определитесь с базовой скоростью на эскулайте - привяжемся к новым количествам.

Вы о чем? Я тестирую на базе 100М записей.
...
Рейтинг: 0 / 0
Ньюсфид для крупной соцсети. SQLite?
    #36541071
MBG
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
MBG
Гость
Siemargl,

Код: plaintext
1.
2.
3.
4.
5.
6.
7.
8.
9.
struct fact_stru
{
	int m_id;
	int m_a1;
	int m_a2;
	int m_a3;
	int m_a4;
	bool operator<(const fact_stru& e )const;
	
};

Нужны 64-бит числа. Иначе нам светит напороться на лимит при активной работе с базой, да и с переносимостью есть проблемы. У эскулайт именно 64 бит int, так что переполнение не грозит.
...
Рейтинг: 0 / 0
Ньюсфид для крупной соцсети. SQLite?
    #36541099
Siemargl
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
MBG,

Лимит чего?
100М записей в память не поместится. Расход 100Мбайт на 1М записей.
Итого для 32 бит без извращений меньше 20М.
...
Рейтинг: 0 / 0
Ньюсфид для крупной соцсети. SQLite?
    #36541113
MBG
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
MBG
Гость
SiemarglMBG,

Лимит чего?

Вставили запись, удалили, снова вставили - 32 бит идентификаторы со временем закончатся. Даже если старые данные на диск сбрасывать, идентификаторы-то должны быть уникальными. При интенсивности вставки 1000 записей в секунду (не вы ли говорили, что это мало?) 32 бит идентификаторов хватит на месяц примерно.

Siemargl
100М записей в память не поместится. Расход 100Мбайт на 1М записей.
Итого для 32 бит без извращений меньше 20М.

Ну вот вы и встали на первые грабли - у топикстартера гигабайты данных в сутки, а у вас в винде 2 Гб на процесс лимит. То есть ваше решение - немасштабируемое, очевидно.

Если вы посмотрите на мои тесты, то в эскулайт на 1М записей плюс 4 индекса по столбцам плюс праймари кей плюс композитный индекс по всем столбцам требуется 73M, притом, что используются 64-бит integer. А у вас 100М на 32-бит integer - разбазариваете вы память, не так ли? Полагаю, с этим все понятно - эскулайт примерно вдвое экономичнее расходует память. Это ваши вторые грабли.

Делайте 64-бит integer и впихивайте сколько влезет записей в память, измеряйте скорость двух вышеназванных селектов, усредняя, скажем, по 1000 итераций. И скорость вставки измеряйте на этой же базе - при 1М записей может работать быстро, а при увеличении количества данных может и начать еще как "тормозить".
...
Рейтинг: 0 / 0
Ньюсфид для крупной соцсети. SQLite?
    #36541123
MBG
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
MBG
Гость
Код: plaintext
1.
2.
3.
4.
5.
6.
7.
void	threadInsert(LPVOID)
	do {
		// start run
		EnterCriticalSection(bufferCritSect);
....
		bool stop = insert1000();
....

А это отнюдь не вставка по одной записи, а пакетная операция. Блокируйте на каждую запись и смотрите скорость вставки 1000 записей на заполненной базе.
...
Рейтинг: 0 / 0
Ньюсфид для крупной соцсети. SQLite?
    #36541129
Siemargl
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Покажете свои цифры, тогда будет видно. Пока что я утверждал только лишь, что в памяти будет на 2 порядка быстрее, чем в базе, а те то, что всю базу надо в ней хранить ))) Это же только кэш - и не более того.

Конечно, в памяти отмасштабируется, сколько есть в системе ОЗУ и не больше. 64Бит ОС и компилятор поможет.
Это серверное решение, а сию секунду я на нетбуке с 512М сижу )
Пока в своп не уходит на 4м мильене - не тормозит.
Завтра днем на рабочем буке погоняю до 10М.

А пока, в общем, Ваш ход.
...
Рейтинг: 0 / 0
Ньюсфид для крупной соцсети. SQLite?
    #36541135
MBG
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
MBG
Гость
SiemarglПокажете свои цифры, тогда будет видно. Пока что я утверждал только лишь, что в памяти будет на 2 порядка быстрее, чем в базе, а те то, что всю базу надо в ней хранить ))) Это же только кэш - и не более того.

Конечно, в памяти отмасштабируется, сколько есть в системе ОЗУ и не больше. 64Бит ОС и компилятор поможет.
Это серверное решение, а сию секунду я на нетбуке с 512М сижу )
Пока в своп не уходит на 4м мильене - не тормозит.
Завтра днем на рабочем буке погоняю до 10М.

А пока, в общем, Ваш ход.

Совершенно некорректно сравнивать, так как я на 100М базе тестирую, а вы на 1М, даже глубина b-tree индексного дерева разная. Но все же:

Код: plaintext
1.
2.
3.
4.
select count(*) from facts where a1= 2  and a2= 2  and a3= 2  and a4= 2 ;
 82 

 36 . 597  microseconds per iteration


Код: plaintext
1.
2.
$ grep -i CPU /proc/cpuinfo 
model name	: Intel(R) Core(TM) 2  Quad CPU    Q6700  @  2 .66GHz
cpu MHz		:  2666 . 804 
...
Рейтинг: 0 / 0
Ньюсфид для крупной соцсети. SQLite?
    #36541141
MBG
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
MBG
Гость
Все же приведу и такой результат:

Код: plaintext
1.
2.
sqlite> select count(*) from facts indexed by facts_a1_idx where a1= 2 ;
 3033113 
CPU Time: user  0 . 516033  sys  0 . 000000 

Здесь итоговая выборка содержит 3М записей.
...
Рейтинг: 0 / 0
Ньюсфид для крупной соцсети. SQLite?
    #36541174
Siemargl
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Даже на нетбуке (ПентиумМ 1.7/ 512М)

2:Inserted: 3000000
1:Simple index count (a1 = 2) = 166402
0:Simpletest a1 = takes 0.031 seconds.

1:Component index count {2,2,2,2} = 33
0:Simpletest a1 = takes 0.000 seconds.

Надо понимать, ваше 0.516 - это полсекунды?
...
Рейтинг: 0 / 0
Ньюсфид для крупной соцсети. SQLite?
    #36541934
MBG
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
MBG
Гость
SiemarglДаже на нетбуке (ПентиумМ 1.7/ 512М)

Это не "даже", а очень плохие результаты. См. ниже.

Siemargl
2:Inserted: 3000000
1:Simple index count (a1 = 2) = 166402
0:Simpletest a1 = takes 0.031 seconds.

1:Component index count {2,2,2,2} = 33
0:Simpletest a1 = takes 0.000 seconds.

Полный бред: "0.000 seconds". Кому нужны такие "измерения"?

SiemarglНадо понимать, ваше 0.516 - это полсекунды?

Да.

У вас 0.031 секунды на 166402 записей в RAM, это будет 0.565 секунды на 3М записей - больше, чем эскулайт тратит на обработку данных в 30-ти кратно большей по размерам дисковой БД!
...
Рейтинг: 0 / 0
Ньюсфид для крупной соцсети. SQLite?
    #36541983
Siemargl
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
MBG,
Вы невнимательны.
0.031с - это время поиска в 3М записей. Выборка же с а1=2 составляет 166402 записи из 3М. Кстати это неточный результат - скорее даже худший - надо было 10 раз прогнать.
0.000с - всего лишь означает, что поиск меньше 1мс

Сейчас прогоню на нормальном железе.

Кроме того, параллельную работу из разных потоков я от Вас не вижу.
...
Рейтинг: 0 / 0
Ньюсфид для крупной соцсети. SQLite?
    #36542012
pavlikkk
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
MBGУ вас 0.031 секунды на 166402 записей в RAM, это будет 0.565 секунды на 3М записей - больше, чем эскулайт тратит на обработку данных в 30-ти кратно большей по размерам дисковой БД!

Железо у вас все-таки разное. Но в то, что бустовые контейнеры могут тормозить на больших объемах данных, охотно верю. Скорее всего, не для того он сделан. А вообще, очень интересная у вас дискуссия.

MBG, я уже говорил, что не имею опыта работы с sqlite. Подскажите, пожалуйста, как грамотно настроить его под такую задачу. Я так понимаю, надо отключить транзакции, поменять размер страницы чтоб соответствовао ОС, еще что-то сделать?
...
Рейтинг: 0 / 0
Ньюсфид для крупной соцсети. SQLite?
    #36542017
MBG
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
MBG
Гость
SiemarglMBG,
Вы невнимательны.
0.031с - это время поиска в 3М записей. Выборка же с а1=2 составляет 166402 записи из 3М. Кстати это неточный результат - скорее даже худший - надо было 10 раз прогнать.

Внимателен. Для сравнимости результатов на вашей мелкой базе делаем простейшую пропорцию: 3033113 записей вернул эскулайт в моем тесте, у вас 166402 записей, значит, ваше время поиска 0.031с нужно увеличить в (3033113/166402) раз, что дает 0.565 секунды. То есть, даже если на больших базах у вас нет регрессии, все равно тормозит.

Siemargl
0.000с - всего лишь означает, что поиск меньше 1мс


В эскулайте поиск на 100М записей выполняется за 36 микросекунд. Какой смысл в таких данных? Ровно так же можно сказать, что у вас поиск занял меньше 1 дня или года, информации - ноль.

SiemarglКроме того, параллельную работу из разных потоков я от Вас не вижу.

Умножайте скорость выборки на число ядер, т.е. на моем железе - на 4. Именно это получаем, когда запускаем 4 экземпляра тестового скрипта - каждый из них выполняется все с той же скоростью, т.к. они никак не взаимодействуют.
...
Рейтинг: 0 / 0
Ньюсфид для крупной соцсети. SQLite?
    #36542107
MBG
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
MBG
Гость
pavlikkkMBGУ вас 0.031 секунды на 166402 записей в RAM, это будет 0.565 секунды на 3М записей - больше, чем эскулайт тратит на обработку данных в 30-ти кратно большей по размерам дисковой БД!

Железо у вас все-таки разное. Но в то, что бустовые контейнеры могут тормозить на больших объемах данных, охотно верю. Скорее всего, не для того он сделан. А вообще, очень интересная у вас дискуссия.

Признаться, я надеялся, что оппонент на С напишет b-tree :-) В этом случае можно получить очень интересные результаты, я когда-то пробовал. Но организация многопоточной работы, поддержка дисковых и in-memory данных, транзакции - слишком много всего нужно для "средней" системы, и в результате эскулайт оказывается и быстрее и намного надежнее.

pavlikkkMBG, я уже говорил, что не имею опыта работы с sqlite. Подскажите, пожалуйста, как грамотно настроить его под такую задачу. Я так понимаю, надо отключить транзакции, поменять размер страницы чтоб соответствовао ОС, еще что-то сделать?

Транзакции в нормальных СУБД не отключаются, это не мускуль :-) Размер страницы ставьте 8к, размер кэша 1 или 2 гига - задается в страницах, пересчитайте. Кэш критичен для вставки - для модификации индексов. Индекс у вас, как я себе представляю, нужен один композитный по полям user_id,save_date.

Продумайте разделение данных по базам - например, по неделям или по месяцам, чтобы в одной базе не хранилось слишком много записей. В данном случае - лучше бы в базе держать не более 20 - 50 миллионов записей. Иначе представьте, что однажды нагрузка подскочит втрое, а у вас и так сотни миллионов записей в одной базе - рискуете огрести самые неприятные проблемы, поскольку на таких масштабах систему не тестировали. В общем, должен быть запас - тестируете на 100М записей - используете 20М, тестируете на 250М - используете 50М.
...
Рейтинг: 0 / 0
Ньюсфид для крупной соцсети. SQLite?
    #36542145
pavlikkk
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
MBG,
Я собственно тоже пробавал написать b-tree, и даже написал. Но как представишь, сколько еще нужно сделать...:)
...
Рейтинг: 0 / 0
Ньюсфид для крупной соцсети. SQLite?
    #36542146
Siemargl
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
MBGSiemarglMBG,
Вы невнимательны.
0.031с - это время поиска в 3М записей. Выборка же с а1=2 составляет 166402 записи из 3М. Кстати это неточный результат - скорее даже худший - надо было 10 раз прогнать.

Внимателен. Для сравнимости результатов на вашей мелкой базе делаем простейшую пропорцию: 3033113 записей вернул эскулайт в моем тесте, у вас 166402 записей, значит, ваше время поиска 0.031с нужно увеличить в (3033113/166402) раз, что дает 0.565 секунды. То есть, даже если на больших базах у вас нет регрессии, все равно тормозит.

Это теория. Count(*) необязательно работает с линейной зависимостью.

MBG
SiemarglКроме того, параллельную работу из разных потоков я от Вас не вижу.

Умножайте скорость выборки на число ядер, т.е. на моем железе - на 4. Именно это получаем, когда запускаем 4 экземпляра тестового скрипта - каждый из них выполняется все с той же скоростью, т.к. они никак не взаимодействуют.
Вот тут код в студию, ибо непонятно как за 100мс запущено несколько потоков. Реализуем задачу по Вашему же ТЗ.

Вот на рабочем буке для 10М.

>Inserted: 10000000
0:Insert 10M takes 64.900 seconds.
---прошла вставка в память 10М записей

0:Simple index count (a1 = 2) = 1111127
0:Simpletest a1 = takes 122 ms.
---10 раз прогнали поиск по условию a1=2 и получили count(*). время на 1 поиск усредненное.

0:Simple index count (a1 = 2) = 1576
0:Simpletest a = {2,2,2,2} takes 4 ms for 100 execs.
---10000 раз прогнали поиск по комплексному ключу и получили count(*). время на 100 поисков усредненное.
...
Рейтинг: 0 / 0
Ньюсфид для крупной соцсети. SQLite?
    #36542451
MBG
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
MBG
Гость
Сделал базу 10М записей согласно тому распределению, что предложено в моем блоге для 10М базы. Результаты:

Код: plaintext
1.
2.
3.
4.
5.
6.
7.
select count(*) from facts where a1= 2  and a2= 2  and a3= 2  and a4= 2 ;
 95  rows
 41 . 87  microseconds per iteration

select count(*) from facts indexed by facts_a1_idx where a1= 2 ;
 554957  rows
 93839 . 0  microseconds per iteration

P.S. Если кучу ваших цифр я правильно понимаю, то вы взяли распределение для 1М базы, а не для 10М. В статье отнюдь не случайно выбраны именно такие распределения.
...
Рейтинг: 0 / 0
Ньюсфид для крупной соцсети. SQLite?
    #36542573
Siemargl
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Да у меня было от 1 до 9 (я менял, а то не сходилось с вашими кол-вами). Но мне же хуже.

Надо понимать, у Вас milliseconds =)

Итого получаем:
Комплексный ключ 41.87ms vs 0.04ms
Простой индекс 93839ms vs 122ms ????

Опять же, приложил exe, может найдете где запустить.
10М записей, распределение поменял на 1..18

Для запуска нужны msvcp90.dll, msvcr90.dll
...
Рейтинг: 0 / 0
Ньюсфид для крупной соцсети. SQLite?
    #36542687
MBG
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
MBG
Гость
SiemarglДа у меня было от 1 до 9 (я менял, а то не сходилось с вашими кол-вами). Но мне же хуже.

Надо понимать, у Вас milliseconds =)


microseconds - это микросекунды.

Итого: комплексный ключ - одинаково, простой индекс в эскулайте быстрее. И это работа с дисковой БД, да и тесты у меня написаны на тикле У вас же структуры в памяти и написано на С++. Так где ваши искомые 2 порядка разницы в быстродействии?
...
Рейтинг: 0 / 0
Ньюсфид для крупной соцсети. SQLite?
    #36542755
Siemargl
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
MBG,

Не верю я в чудеса. Вечером соберу эскулайт.

А то непорядок, оракл - есть, mssql - есть, access- есть, sybase sa - есть, fb - есть, даже Hytech завалялся, а вот самого быстрого sqlite (собранного) - нету. Безобразие !
...
Рейтинг: 0 / 0
Ньюсфид для крупной соцсети. SQLite?
    #36542785
MBG
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
MBG
Гость
SiemarglMBG,

Не верю я в чудеса. Вечером соберу эскулайт.

А то непорядок, оракл - есть, mssql - есть, access- есть, sybase sa - есть, fb - есть, даже Hytech завалялся, а вот самого быстрого sqlite (собранного) - нету. Безобразие !

Это разве чудеса. Вот токиокабинет, по тестам его автора, вдесятеро эскулайт обгоняет на чтении :-) А вставки выполняет почти с той же скоростью, что и выборки :-)
...
Рейтинг: 0 / 0
Ньюсфид для крупной соцсети. SQLite?
    #36542864
Фотография Dmitry Arefiev
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
А что же тогда форум не переименовать в Tokyo Cabinet, не забыть
про этот тормозной SQLite, и не переключить весь код на Tokyo Cabinet ?
...
Рейтинг: 0 / 0
Ньюсфид для крупной соцсети. SQLite?
    #36542893
MBG
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
MBG
Гость
Dmitry ArefievА что же тогда форум не переименовать в Tokyo Cabinet, не забыть
про этот тормозной SQLite, и не переключить весь код на Tokyo Cabinet ?

Если на движке токиокабинет сделать реляционную СУБД, то преимущества в скорости пропадут. Но тестовую реализацию от Siemargl вполне разумно сравнивать как раз с токиокабинет, а не эскулайт - и тогда явно видно, что буст сделан паршивенько, ибо как раз в таком тесте решение без sql, транзакционности, проверки целостности и проч. просто обязано обогнать эскулайт.
...
Рейтинг: 0 / 0
Ньюсфид для крупной соцсети. SQLite?
    #36543284
Siemargl
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Повозился блин, с dll-кой и кодировкой.

Итого получаем:
Комплексный ключ 15.6-0ms vs 0.04ms
Простой индекс 171-230ms vs 122ms

И 25 минут на создание базы с индексами =)

Использование памяти 32М+772Мб база vs 1100Mb RAM

В общем выгоды на поиске мало, выигрыш только на создании базы - где дисковые операции.

логEnter SQL statements terminated with a ";"
sqlite> .load tablefunc.dll
sqlite> .timer ON
sqlite> pragma page_size;
1024
CPU Time: user 0.000000 sys 0.000000
sqlite> pragma page_size = 4096;
CPU Time: user 0.000000 sys 0.000000
sqlite> pragma page_size;
4096
CPU Time: user 0.000000 sys 0.000000
sqlite> pragma cache_size;
2000
CPU Time: user 0.000000 sys 0.000000
sqlite> pragma cache_size = 400000;
CPU Time: user 0.000000 sys 0.000000
sqlite> pragma cache_size;
400000
CPU Time: user 0.000000 sys 0.000000
sqlite> create temp table tmp_facts(rowid int);
CPU Time: user 0.000000 sys 0.000000
sqlite> select intrange2table (1,10000000,1,'tmp_facts');
CPU Time: user 112.788723 sys 430.500360
sqlite> create table facts(a1 int,a2 int,a3 int,a4 int);
CPU Time: user 0.000000 sys 0.000000
sqlite> insert into facts
...> select
...> cast(abs(random())/9223372036854775807.*18 as int),
...> cast(abs(random())/9223372036854775807.*18 as int),
...> cast(abs(random())/9223372036854775807.*18 as int),
...> cast(abs(random())/9223372036854775807.*18 as int)
...> from tmp_facts;
CPU Time: user 42.713074 sys 1.185608
sqlite> create index facts_a1_idx on facts(a1);
CPU Time: user 68.624840 sys 0.702005
sqlite> create index facts_a3_idx on facts(a3);
CPU Time: user 68.250438 sys 0.530403
sqlite> create index facts_a2_idx on facts(a2);
CPU Time: user 68.702840 sys 0.514803
sqlite> create index facts_a4_idx on facts(a4);
CPU Time: user 67.127230 sys 0.577204
sqlite> select count(*) from facts where a1=2 and a2=2 and a3=2 and a4=2;
112
CPU Time: user 1.138807 sys 0.000000
sqlite> select count(*) from facts where a1=2;
555739
CPU Time: user 0.171601 sys 0.000000
sqlite> select count(*) from facts where a1=2;
555739
CPU Time: user 0.234002 sys 0.000000
sqlite> select count(*) from facts where a1=2;
555739
CPU Time: user 0.280802 sys 0.000000
sqlite> select count(*) from facts where a1=2;
555739
CPU Time: user 0.171601 sys 0.000000
sqlite> create index facts_complex_idx on facts(a1,a2,a3,a4);
CPU Time: user 97.765827 sys 1.092007
sqlite> select count(*) from facts indexed by facts_a1_idx where a1=2;
555739
sqlite> select count(*) from facts where a1=2 and a2=2 and a3=2 and a4=2;
112
CPU Time: user 0.015600 sys 0.000000
sqlite> select count(*) from facts where a1=2 and a2=2 and a3=2 and a4=2;
112
CPU Time: user 0.000000 sys 0.000000
...
Рейтинг: 0 / 0
Ньюсфид для крупной соцсети. SQLite?
    #36543285
Siemargl
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
И может чего выиграется при фетче данных из базы.
...
Рейтинг: 0 / 0
Ньюсфид для крупной соцсети. SQLite?
    #36543323
MBG
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
MBG
Гость
Siemargl,

Код: plaintext
1.
2.
3.
4.
5.
sqlite> select count(*) from facts where a1= 2  and a2= 2  and a3= 2  and a4= 2 ;
 112 
CPU Time: user  0 . 015600  sys  0 . 000000 
sqlite> select count(*) from facts where a1= 2  and a2= 2  and a3= 2  and a4= 2 ;
 112 
CPU Time: user  0 . 000000  sys  0 . 000000 

Здесь первый результат не показателен - видно операционка чем-то своим была занята. Если выполните этот запрос несколько раз, убедитесь сами.

Собственно, за то и ценю эскулайт, что он замечательно работает с дисковыми базами - когда размер БД и, особенно, выборок, превышает размер ОЗУ, это критично. А вот вставка данных - ахиллесова пята, при наличии нескольких индексов и больших таблицах скорость вставки деградирует сильно (у меня в блоге есть тесты на этот счет, если интересно). Для индекса по паре полей (число+дата, к примеру) разумно ограничиться размером таблицы около 100М записей. Плюс стараться выполнять модифицирующие операции в пакетном режиме. Так что за все приходится платить, "серебряной пули" нет.
...
Рейтинг: 0 / 0
Ньюсфид для крупной соцсети. SQLite?
    #36544142
pavlikkk
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
MBG,
протестил я токиокабинет. думал, вот оно, то что мне надо, когда встретил их "рекламу":)

В результате, эта хрень вообще не может работать с большим объемом данных. Если ничего не тюнить, то начинает тормозить уже на 100000 записей, причем время вставки растет явно быстрее чем линейно, скорее экспоненциально. Потрахавшись с настройками, выделив здоровый кеш и размер bucket'a в b-дереве, удалось затолкать туда 23 миллиона записей, дальше не реально. Короче, работает она только до тех пор, пока структуры данных в память помещаются. При этом, никакой гарантии целостности данных:

отрывок из "tcbdb.h"
Код: plaintext
1.
2.
3.
4.
5.
6.
7.
  bool tcbdbclose(TCBDB *bdb);
/* Close a B+ tree database object.
   `bdb' specifies the B+ tree database object.
   If successful, the return value is true, else, it is false.
   Update of a database is assured to be written when the database is closed.  If a writer opens
   a database but does not close it appropriately, the database will be broken. 
*/

В общем, дерьмо. Моя собственная поделка и то лучше работает на объемах в 10 раз больших. Вот еще ссылка на тесты "мега-крутой" токиокабинет: http://www.dmo.ca/blog/benchmarking-hash-databases-on-large-data/

Точно такая же проблема. В общем, никому не рекомендую.
...
Рейтинг: 0 / 0
Ньюсфид для крупной соцсети. SQLite?
    #36544371
MBG
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
MBG
Гость
Результаты тестов для хэшей мне кажутся невероятными - такая ситуация типична для b-tree, но не для хэшей. Плюс не сделано даже попытки пообщаться с автором токиокабинет, что опять же не внушает доверия.

Кстати, для CDB существует обертка, позволяющая модифицировать CDB-базы, а не только как константные использовать.
...
Рейтинг: 0 / 0
Ньюсфид для крупной соцсети. SQLite?
    #36544474
Siemargl
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
MBGSiemarglMBG,

Давайте постановку задачи (с достаточным упрощением) и проверим порядок. Блокироваться в памяти быстрее, чем блокироваться в кэше БД и в блоках на диске.
Только реализации задачи на SQL с Вас.

Например, вот такой тест:
Тестирование SQLite 3.6.17-mobigroup.2 на больших таблицах

У вас - с многопоточной модификацией in-memory структуры при добавлении по одной записи, с частотой 1000 записей в секунду, с поддержкой индексов по полям и композитного (как описано в статье).

У меня - добавление записей пакетное ежесекундно, число записей в "пакете" - 1000. Для измерения скорости запросов скриптик напишу и статью дополню.

Измеряем:
1. Коэффициент доступности в процентах. Например, 80% означает, что 80% времени данные доступны для выборки или что данные блокируются на 0,2 секунды ежесекундно.
2. Скорость выборки набора записей, удовлетворяющих условию (запрос по одному индексу и по композитному, как в статье). В SQL делаю count(*), чтобы избежать затрат времени на передачу извлеченных данных - т.е. измеряется только время непосредственно выборки.

Предлагаю таки закончить по данному заданию. С небольшими уточнениями
-тестируем на готовой базе 10М
-добавление записей происходит 100 потоками по 1000 записей в сек
-1 поток читающий - select sum(a1+a2+a3+a4) from facts where a1=2
-ну и конечно ai - 64бит
...
Рейтинг: 0 / 0
Ньюсфид для крупной соцсети. SQLite?
    #36544518
MBG
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
MBG
Гость
pavlikkkMBG,
протестил я токиокабинет. думал, вот оно, то что мне надо, когда встретил их "рекламу":)

В результате, эта хрень вообще не может работать с большим объемом данных. Если ничего не тюнить, то начинает тормозить уже на 100000 записей, причем время вставки растет явно быстрее чем линейно, скорее экспоненциально. Потрахавшись с настройками, выделив здоровый кеш и размер bucket'a в b-дереве, удалось затолкать туда 23 миллиона записей, дальше не реально. Короче, работает она только до тех пор, пока структуры данных в память помещаются.
...
Вот еще ссылка на тесты "мега-крутой" токиокабинет: http://www.dmo.ca/blog/benchmarking-hash-databases-on-large-data/

Точно такая же проблема. В общем, никому не рекомендую.

Так, сначала про эскулайт были желающие на два порядка лучше решение сделать, теперь то же самое с токиокабинет? Сейчас посмотрим...

Запускаю тесты, база токиокабинет типа хэш на 10М записей размером 690M создается за 134 секунды, на 20М записей размером 996M - за 280 секунд. Это на ноуте с так себе винтом и процессором. Вполне себе достойная скорость, никакого падения производительности в помине нет.

Может, не надо с настройками трахаться, а лучше маны почитать?

P.S. Одна верная мысль вами названа, но вы сами не поняли ее глубины. А именно "пока структуры данных в память помещаются". Только вот здесь "структуры данных" - не то, что вы думаете. В эскулайте, кстати, аналогично.
...
Рейтинг: 0 / 0
Ньюсфид для крупной соцсети. SQLite?
    #36544554
MBG
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
MBG
Гость
Siemargl
Предлагаю таки закончить по данному заданию. С небольшими уточнениями
-тестируем на готовой базе 10М
-добавление записей происходит 100 потоками по 1000 записей в сек
-1 поток читающий - select sum(a1+a2+a3+a4) from facts where a1=2
-ну и конечно ai - 64бит

Это вы в памяти добавляете в 100 потоков, а у нас в базу пишется пакетно из одного потока - жесткий диск он не резиновый. А вот ридеров - много, скажем, 1000 потоков. Смотреть для одного читающего потока смысла нет, посколько в вебе на каждую операцию записи приходится, как минимум, десяток операций чтения. Выборку делать по композитному индексу, т.к. выбирать порядка миллиона результатов "where a1=2" на практике смысла не имеет, эдак мы скорость ввода-вывода тестировать будем (для вас этот тест вообще оптимально кодируется полным перебором).
...
Рейтинг: 0 / 0
Ньюсфид для крупной соцсети. SQLite?
    #36544816
Siemargl
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
MBG,

Смысл не столько в абсолютной скорости, а задержках при работе с кэшем и системными вызовами sqlite - пусть кэш будет любого размера.

Может быть трафик на запись можно взять поменьше, чтобы до диска почти не доставало. Но ограничиваться читателями нельзя - чтение то неблокируемое, а померять хотим блокировку.
...
Рейтинг: 0 / 0
Ньюсфид для крупной соцсети. SQLite?
    #36544907
pavlikkk
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
MGB, хорошо, может я не прав. Дайте мне исходники тестов, я попробую прогнать у себя. Загоните в него 100М записей, по 10М за раз. Между ними закрывая базу.

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

Код: plaintext
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.
27.
28.
29.
30.
31.
32.
33.
34.
35.
36.
37.
38.
39.
40.
41.
42.
43.
44.
45.
46.
47.
48.
49.
50.
51.
52.
53.
54.
55.
56.
57.
58.
59.
60.
61.
62.
63.
64.
65.
66.
67.
68.
std::string gen_random_text(int maxlen)
{
    int len = random() % maxlen +  1 ;
    char str[maxlen+ 1 ];

    memset(str, 0x00, maxlen+ 1 );

    for (int i =  0 ; i < len; ++i)
    {
        str[i] = 0x41 + (random() %  20 );
    }

    return str;

}

int main(int argc, char** argv)
{
    simple_timer t("whole time");

    TCBDB *bdb = tcbdbnew();    

    if (!tcbdbsetcache(bdb, 0xFFFF, 0x1FFFF))
    {
        printf("cant open: error %s\n", tcbdberrmsg(tcbdbecode(bdb)));
        return - 1 ;
    }

    if (!tcbdbtune(bdb,  0 ,  0 , 0x1FFFF, - 1 , - 1 , BDBTLARGE))
    {
        printf("cant open: error %s\n", tcbdberrmsg(tcbdbecode(bdb)));
        return - 1 ;
    }

    if (!tcbdbopen(bdb, "tokyo.tcb", BDBOREADER|BDBOWRITER|BDBOCREAT))
    {
        printf("cant open: error %s\n", tcbdberrmsg(tcbdbecode(bdb)));
        return - 1 ;
    }

    logr.level = sev_trace;
    { simple_timer t("insert");

    for (int i =  0 ; i < atoi(argv[ 1 ]); ++i)
    {
        int id = random()% 1000000 ;
        std::string text = gen_random_text( 64 );

        if (!tcbdbputdup(bdb, &id, sizeof(int), text.data(), text.size()))
        {
            printf("cant put: error %s\n", tcbdberrmsg(tcbdbecode(bdb)));
            return - 1 ;
        }

        if ((i% 200000 )== 0 )
            printf("%d completed\n", i);
     }

     }

    if (!tcbdbclose(bdb))
    {
        printf("cant close: error %s\n", tcbdberrmsg(tcbdbecode(bdb)));
        return - 1 ;
    }

    return  0 ;
}

Прогоните мой тест, не получив падения производительности. И приведите исходники своего теста. Умные все такие..
...
Рейтинг: 0 / 0
Ньюсфид для крупной соцсети. SQLite?
    #36544908
MBG
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
MBG
Гость
SiemarglMBG,

Смысл не столько в абсолютной скорости, а задержках при работе с кэшем и системными вызовами sqlite - пусть кэш будет любого размера.

Может быть трафик на запись можно взять поменьше, чтобы до диска почти не доставало. Но ограничиваться читателями нельзя - чтение то неблокируемое, а померять хотим блокировку.

По дефолту эскулайт делает полный сброс данных на диск, с получением подтверждения от ОС. Это очень затратная операция, хоть 1 байт записывается, хоть мегабайт. Потому необходимо данные записывать пакетно. Если же fsync отключить, то при сбое ОС или приложения есть вероятность повреждения БД. Это ограничение действует для всех приложений. К примеру, у постгреса это параметр fsync в конфиге.

Проверить блокировки можно, отключив гарантированную синхронизацию записи, но для продакшена это не интересно.
...
Рейтинг: 0 / 0
Ньюсфид для крупной соцсети. SQLite?
    #36544938
pavlikkk
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
MGB
P.S. Одна верная мысль вами названа, но вы сами не поняли ее глубины. А именно "пока структуры данных в память помещаются". Только вот здесь "структуры данных" - не то, что вы думаете. В эскулайте, кстати, аналогично.

Один вы, о гуру, понимаете всю глубину. Прозрев взглядом, что именно я думаю, говоря "структуры данных":)
...
Рейтинг: 0 / 0
Ньюсфид для крупной соцсети. SQLite?
    #36544942
MBG
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
MBG
Гость
pavlikkk,

В комплекте с токиокабинет предлагается набор тестовых программ. В том числе tchtest. Покажите ваши результаты tchtest для 20М базы.
...
Рейтинг: 0 / 0
Ньюсфид для крупной соцсети. SQLite?
    #36544949
Siemargl
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
MBG
Проверить блокировки можно, отключив гарантированную синхронизацию записи, но для продакшена это не интересно.
Это можно воспринимать, как добровольную сдачу (resign) для задачи ТС (и своей) ? =)
...
Рейтинг: 0 / 0
Ньюсфид для крупной соцсети. SQLite?
    #36545003
pavlikkk
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
MBG,
не могу показать результаты для 20M базы. Вот на этом месте подвисло и висит уже минут 10. C каждым миллионом работает ощутимо медленнее.

/usr/ports/databases/tokyocabinet/work/tokyocabinet-1.4.41/tchtest write tt.tbd 10000000
<Writing Test>
seed=2592105062 path=tt.tbd rnum=10000000 bnum=-1 apow=-1 fpow=-1 mt=0 opts=0 rcnum=0 xmsiz=-1 dfunit=0 omode=0 as=0 rnd=0

......................... (01000000)
......................... (02000000)
......................... (03000000)
......................... (04000000)
......................... (05000000)
......................... (06000000)
......................... (07000000)
..............

FreeBSD 7.2-STABLE FreeBSD 7.2-STABLE #1: Mon Oct 5 10:33:30 UTC 2009 amd64
...
Рейтинг: 0 / 0
Ньюсфид для крупной соцсети. SQLite?
    #36545010
pavlikkk
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
MGB, объясните мне убогому, как же это оно у вас так быстро и хорошо работает? Мож нам на продакшен ваш ноут поставить?
...
Рейтинг: 0 / 0
Ньюсфид для крупной соцсети. SQLite?
    #36545051
MBG
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
MBG
Гость
SiemarglMBG
Проверить блокировки можно, отключив гарантированную синхронизацию записи, но для продакшена это не интересно.
Это можно воспринимать, как добровольную сдачу (resign) для задачи ТС (и своей) ? =)

Что-то вы путаете - топикстартеру я в самом начале описал реализацию на основе пакетной записи на диск. И если поискать у меня в деб-репозитории, то можно найти реализацию на тикле коллектора лога с множества АТС с in-memory БД, синхронизируемой с дисковой. Вполне себе продакшен-решение, давно и успешно работает.

Заметьте - конкурентный доступ _работает_, но для многих миллионов записей в сутки _эффективнее_ делать пакетные модификации.
...
Рейтинг: 0 / 0
Ньюсфид для крупной соцсети. SQLite?
    #36545055
Siemargl
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
pavlikkk, Память свободная есть?
...
Рейтинг: 0 / 0
Ньюсфид для крупной соцсети. SQLite?
    #36545067
pavlikkk
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
Siemargl,
2 Гб свободной памяти.
...
Рейтинг: 0 / 0
Ньюсфид для крупной соцсети. SQLite?
    #36545127
MBG
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
MBG
Гость
pavlikkkMGB, объясните мне убогому, как же это оно у вас так быстро и хорошо работает? Мож нам на продакшен ваш ноут поставить?

Ну, ноут-то ладно, главное меня не трогать :-)

Все просто - я начал с пятиминутного чтения мана:

"Tokyo Cabinet: a modern implementation of DBM"Effective Implementation of Hash Database
Tokyo Cabinet uses hash algorithm to retrieve records. If a bucket array has sufficient number of elements, the time complexity of retrieval is "O(1)". That is, time required for retrieving a record is constant, regardless of the scale of a database. It is also the same about storing and deleting. Collision of hash values is managed by separate chaining. Data structure of the chains is binary search tree. Even if a bucket array has unusually scarce elements, the time complexity of retrieval is "O(log n)".

Как видите, я взял такие параметры, чтобы попасть в O(1). А у вас скорость определяется O(log n) при большом n.


Код: plaintext
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.
27.
28.
29.
30.
31.
32.
33.
$ tchtest write test.db  20000000   20000000 
<Writing Test>
  path=test.db  rnum= 20000000   bnum= 20000000   apow=- 1   fpow=- 1   mt= 0   opts= 0   rcnum= 0   omode= 0   as= 0 

......................... ( 02000000 )
......................... ( 04000000 )
......................... ( 06000000 )
......................... ( 08000000 )
......................... ( 10000000 )
......................... ( 12000000 )
......................... ( 14000000 )
......................... ( 16000000 )
......................... ( 18000000 )
......................... ( 20000000 )
record number:  20000000 
size:  723890448 
bucket number:  20971507 
used bucket number:  13880741 
cnt_writerec:  20000000 
cnt_reuserec:  0 
cnt_moverec:  0 
cnt_readrec:  6909116 
cnt_searchfbp:  20000000 
cnt_insertfbp:  0 
cnt_splicefbp:  0 
cnt_dividefbp:  0 
cnt_mergefbp:  0 
cnt_reducefbp:  0 
cnt_appenddrp:  0 
cnt_deferdrp:  0 
cnt_flushdrp:  0 
cnt_adjrecc:  0 
time:  197 . 216 
ok

Если взять вдвое меньше ячеек, время окажется равным 537 секунд. И так далее. Подсчет вероятности коллизии и, соответственно, времени на вставку в зависимости от числа ячеек приведен в упомянутом выше руководстве, равно как и рекомендация взять число ячеек равным половине от кол-ва записей в базе.
...
Рейтинг: 0 / 0
Ньюсфид для крупной соцсети. SQLite?
    #36545139
MBG
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
MBG
Гость
pavlikkkMGB
P.S. Одна верная мысль вами названа, но вы сами не поняли ее глубины. А именно "пока структуры данных в память помещаются". Только вот здесь "структуры данных" - не то, что вы думаете. В эскулайте, кстати, аналогично.

Один вы, о гуру, понимаете всю глубину. Прозрев взглядом, что именно я думаю, говоря "структуры данных":)

Пойдем простым логическим путем: думаете вы не то, что написано в мане, иначе результаты не были бы столь плачевны :-)
...
Рейтинг: 0 / 0
Ньюсфид для крупной соцсети. SQLite?
    #36545325
pavlikkk
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
MBG,
попробуйте лучше вот это и расскажите про результаты. оно больше соответствует моим тестам.
/usr/ports/databases/tokyocabinet/work/tokyocabinet-1.4.41/tchtest rcat tt.tbd 10000000 20000000

Тоже o(1) ?
...
Рейтинг: 0 / 0
Ньюсфид для крупной соцсети. SQLite?
    #36545362
MBG
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
MBG
Гость
pavlikkkMBG,
попробуйте лучше вот это и расскажите про результаты. оно больше соответствует моим тестам.
/usr/ports/databases/tokyocabinet/work/tokyocabinet-1.4.41/tchtest rcat tt.tbd 10000000 20000000

Тоже o(1) ?

А тут вы врубили алгоритм слияния при конфликтах - в итоге словили кучу операций перезаписи и перемещения - выполняется обновление на месте с перемещением кучи блоков, чтобы освободить место. Имхо практически это можно применить разве что в синтетических тестах SSD vs. HDD.
...
Рейтинг: 0 / 0
Ньюсфид для крупной соцсети. SQLite?
    #36545477
pavlikkk
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
Мда, с высоты моих 22 лет эти слова не понять. В общем, не рабочая это хрень. По всем моим теста, а не тем, которые они приводят у себя в пакете. Причем, это не только мое мнение, а всех, кто пытался использовать на продашене. Ссылки давать не буду, кому надо сами посмотрят.

Тем не менее, cпасибо за дельные советы по sqlite!:)
...
Рейтинг: 0 / 0
69 сообщений из 69, показаны все 3 страниц
Форумы / SQLite [игнор отключен] [закрыт для гостей] / Ньюсфид для крупной соцсети. SQLite?
Найденые пользователи ...
Разблокировать пользователей ...
Читали форум (0):
Пользователи онлайн (0):
x
x
Закрыть


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