Есть ли способ ускорить загрузку в Berkeley DB?

Теперь я использую Berkeley DB для создания Btree, хранящего 80 миллионов записей. Мне нужно вставить их, отсканировать и обновить их значения. Однако только обновление занимает около 1 часа, что для меня слишком медленно. В https://docs.oracle.com/cd/E17076_05/html/gsg/CXX/BerkeleyDB-Core-Cxx-GSG.pdf сказано, что каждая операция чтения в Berkeley DB загружает в память целую страницу. Интересно, есть ли способы этого избежать? То есть каждый раз, когда я хочу получить запись, в память будет загружаться только ее пара ключа и данных, а не вся страница, содержащая ее? Спасибо.

Привет, Кайджи, добро пожаловать в Stack Overflow! Похоже, вы работаете на грани возможностей BDB, но это полностью зависит от размера ваших записей. При 80 миллионах записей в час у вас будет около 45 микросекунд на запись. Это может быть «неплохо», если ваши записи имеют размер в килобайтах. Какой диапазон размеров для ваших ключей и ваших данных? И какой у вас установлен размер страницы BDB? Вы обязательно должны прочитать всю конечную страницу и, возможно, несколько страниц индекса. Но вы можете изменить размер страницы, чтобы она лучше соответствовала вашим записям.

Mike Andrews 30.09.2018 04:08

@MikeAndrews Спасибо, Майк. Мой ключ - это структура, состоящая из 3 беззнаковых int (я думаю, что это 12 байт). а для значения он включает беззнаковый int и указатель void (я думаю, 8 байтов, указатель всегда устанавливается в NULL для дальнейшего расширения). Страница BDB установлена ​​на 4 КБ, размер блока ввода-вывода моего сервера. Есть ли у вас какие-либо мнения по поводу повышения эффективности? Спасибо.

Kaijie Zhu 01.10.2018 11:03

@MikeAndrews Кстати, "подготовка индекса" фактически включает 1 вставку и 2 обновления. То есть он состоит из 3 шагов: (1) вставить все 80 миллионов записей в набор данных (2) сканировать с начала записи в индексе и обновлять их значения одну за другой (3) другое сканирование с начала и обновлять их значение по одному. Объем памяти ограничен всего 2 ГБ, поэтому я думаю, что сейчас операция ввода-вывода - это основная часть программы. И размер набора данных составляет 2 ГБ. После того, как все вставлено, файл .db составляет около 5 ГБ.

Kaijie Zhu 01.10.2018 11:17

Вам нужно будет вызвать в свое приложение, но один из способов улучшить производительность записи - это уменьшить агрессивность базы данных. Если вам вообще не нужна атомарность, вы можете работать без транзакций. Если вам нужна атомарность, но вы можете терпеть несколько потерянных записей при восстановлении, попробуйте флаг DB_TXN_WRITE_NOSYNC или даже DB_TXN_NOSYNC (см. Этот ответ: stackoverflow.com/questions/3825022/…).

Mike Andrews 01.10.2018 15:28

И здорово, что размер страницы соответствует размеру блочного ввода-вывода для вашего сервера! Я бы не стал этого менять. Если бы ваши записи были большими, и вы постоянно переполнялись, вы могли бы перейти к большему размеру страницы. Но размер 4K настолько мал, насколько вам хотелось бы, даже для очень маленьких ключей / данных, как у вас.

Mike Andrews 01.10.2018 15:31

Другой вариант, хотя он и начинает немного терять смысл наличия такой базы данных, - это «складывать» ваши записи в более крупные логические записи. Если бы вы могли сгруппировать свои записи в ячейки по 64, относясь к BDB как к хеш-таблице, то вы бы сократили количество вставок с 80 миллионов до 1,25 миллиона. Для вашего приложения эта запись будет иметь размер около килобайта и при этом легко уместиться на странице.

Mike Andrews 01.10.2018 15:36

@MikeAndrews Спасибо. Я не использовал DBenv. Поэтому считаю, что транзакций быть не должно. Является ли?

Kaijie Zhu 01.10.2018 19:48

Ах, ну уж точно логов без окружения не бывает. Можно подумать, что это лучший вариант для Berkeley DB! (в стороне, убедитесь, что вы установили размер кеша с помощью DB-> set_cachesize ().) Но, если вы не используете транзакции или среду ... может быть, вам не нужна Berkeley DB? Я имею в виду, что вы жестяная банка заставляете BDB работать быстро, но вы потратите на это кучу своей жизненной энергии. Вы могли бы вместо этого оценить LMDB или другое современное хранилище ключей / значений?

Mike Andrews 01.10.2018 20:31

@MikeAndrews En, мне очень жаль. Я не использовал DB-> set_cache, а размер по умолчанию для BDB составляет 256 КБ. Это имеет значение? Я не совсем понимаю его влияние.

Kaijie Zhu 02.10.2018 22:05

Ах, да! Вы захотите установить его настолько большим, насколько сможете. Если у вас 2 ГБ ОЗУ, оставьте место для операционной системы и всего остального, что есть в системе. Если вы можете получить его выше 1 ГБ, ваша программа должна быть намного, намного счастливее.

Mike Andrews 03.10.2018 03:28
ReactJs | Supabase | Добавление данных в базу данных
ReactJs | Supabase | Добавление данных в базу данных
Это и есть ваш редактор таблиц в supabase.👇
1
10
130
0

Другие вопросы по теме