Redis
 sql >> Baza danych >  >> NoSQL >> Redis

Redis 10 razy większe zużycie pamięci niż danych

Cóż, tego oczekuje się od każdego wydajnego przechowywania danych:słowa muszą być indeksowane w pamięci w dynamicznej strukturze danych z komórek połączonych wskaźnikami. Rozmiar metadanych struktury, wskaźników i wewnętrznej fragmentacji alokatora pamięci jest powodem, dla którego dane zajmują znacznie więcej pamięci niż odpowiadający im plik płaski.

Zestaw Redis jest zaimplementowany jako tablica mieszająca. Obejmuje to:

  • tablica wskaźników rosnących geometrycznie (potęgi dwójki)
  • Druga tablica może być wymagana, gdy aktywne jest ponowne haszowanie
  • połączone komórki listy reprezentujące wpisy w tablicy mieszającej (3 wskaźniki, 24 bajty na wpis)
  • Redis wrappery obiektów (jeden na wartość) (16 bajtów na wpis)
  • same rzeczywiste dane (każdy z nich jest poprzedzony 8 bajtami dla rozmiaru i pojemności)

Wszystkie powyższe rozmiary są podane dla implementacji 64-bitowej. Uwzględniając narzut alokatora pamięci, powoduje to, że Redis pobiera co najmniej 64 bajty na element zestawu (oprócz danych) dla najnowszej wersji Redis przy użyciu alokatora jemalloc (>=2.4)

Redis zapewnia optymalizacje pamięci dla niektórych typów danych, ale nie obejmują one zestawów ciągów. Jeśli naprawdę potrzebujesz zoptymalizować zużycie pamięci przez zestawy, istnieją triki, których możesz użyć. Nie zrobiłbym tego dla zaledwie 160 MB pamięci RAM, ale jeśli masz większe dane, oto, co możesz zrobić.

Jeśli nie potrzebujesz możliwości sumowania, przecięcia, różnicowania zbiorów, możesz przechowywać swoje słowa w obiektach haszujących. Zaletą jest to, że obiekty haszujące mogą być automatycznie optymalizowane przez Redis przy użyciu zipmap, jeśli są wystarczająco małe. Mechanizm zipmap został zastąpiony listą zip w Redis>=2.6, ale idea jest taka sama:użycie zserializowanej struktury danych, która może zmieścić się w pamięci podręcznej procesora, aby uzyskać zarówno wydajność, jak i kompaktowe zużycie pamięci.

Aby zagwarantować, że obiekty haszujące są wystarczająco małe, dane mogą być dystrybuowane zgodnie z pewnym mechanizmem haszującym. Zakładając, że musisz przechowywać 1 mln elementów, dodanie słowa można zaimplementować w następujący sposób:

  • hash it modulo 10000 (wykonane po stronie klienta)
  • HMSET słowa:[hasznum] [słowo] 1

Zamiast przechowywać:

words => set{ hi, hello, greetings, howdy, bonjour, salut, ... }

możesz przechowywać:

words:H1 => map{ hi:1, greetings:1, bonjour:1, ... }
words:H2 => map{ hello:1, howdy:1, salut:1, ... }
...

Aby pobrać lub sprawdzić istnienie słowa, jest ono takie samo (zahaszuj je i użyj HGET lub HEXISTS).

Dzięki tej strategii można uzyskać znaczne oszczędności pamięci, pod warunkiem, że moduł skrótu jest wybrany zgodnie z konfiguracją zipmap (lub listą zip dla Redis>=2.6):

# Hashes are encoded in a special way (much more memory efficient) when they
# have at max a given number of elements, and the biggest element does not
# exceed a given threshold. You can configure this limits with the following
# configuration directives.
hash-max-zipmap-entries 512
hash-max-zipmap-value 64

Uwaga:nazwy tych parametrów zmieniły się wraz z Redis>=2.6.

Tutaj modulo 10000 dla 1M elementów oznacza 100 elementów na obiekt hash, co gwarantuje, że wszystkie z nich są przechowywane jako zipmapy/listy zip.



  1. Redis
  2.   
  3. MongoDB
  4.   
  5. Memcached
  6.   
  7. HBase
  8.   
  9. CouchDB
  1. Aby rozpocząć ładowanie YCSB z włączoną opcją klastra dla REDIS

  2. Przynieś własne konta Azure — hosting dla MongoDB® i Redis™ w ScaleGrid

  3. jak zdobyć klucze, które nie pasują do konkretnego wzoru w redis?

  4. Wydajny pamięciowo sposób przechowywania 32-bitowych liczb całkowitych ze znakiem w Redis

  5. Jak wdrożyć resque workerów do produkcji?