Какая база данных полезна для замены набора пустых массивов? - PullRequest
1 голос
/ 21 февраля 2012

Мой код создает dict (со строками в качестве ключей и числовыми массивами в качестве значений), который слишком велик и не помещается в ОЗУ, поэтому программа аварийно завершает работу («Невозможно выделить память», «убито», « прервана ").

Прочитав несколько SO статей, у меня сложилось впечатление, что мне нужно будет использовать базу данных для обработки этого случая. Но какой я должен использовать? bsddb - интерфейс с библиотекой Berkeley DB рекомендуется @ Python Disk-Based Dictionary принимает только строки в качестве значений, что делает его очень громоздким при использовании его с массивными массивами. Я также кратко рассмотрел sqlite3 , рекомендованный @ Как справиться с нехваткой памяти с помощью Python , но я действительно хотел бы избежать использования SQL для доступа к моим данным.

Что бы вы порекомендовали?

Ответы [ 2 ]

1 голос
/ 21 февраля 2012

sqlite показалось бы идеальным, учитывая, что ваш шаблон запроса будет очень простым.

Другой вариант, который я часто упоминаю, - это redis (http://redis.io), сервер значения ключа.

Memcached (http://memcached.org/) и MongoDB (http://www.mongodb.org/) - другие популярные базы данных NoSQL.

Если ни один из них вам не по вкусу, посмотрите в Google NoSQL, какие еще проекты существуют.

0 голосов
/ 21 февраля 2012

Вот простое решение, которое может работать на вас. Вместо того, чтобы хранить массивы в dict (чтобы они были в памяти), запишите их в файл. Пока вы осторожны со своими ссылками, они будут очищаться счетчиком ссылок, пока вы не получите к ним доступ снова.

РЕДАКТИРОВАТЬ: Вы можете настроить это, используя npz файлы для хранения нескольких ключей одновременно, особенно если вам не нужен произвольный доступ.

Код

import tempfile
import numpy

class numpy_dict(dict):
    def __setitem__(self, key, value):
        with tempfile.NamedTemporaryFile(delete=False) as f:
            numpy.save(f, value)
            super(numpy_dict, self).__setitem__(key, f.name)

    def __getitem__(self, key):
        path = super(numpy_dict, self).__getitem__(key)
        return numpy.load(path)

Пример использования

>>> import so
>>> import numpy as np
>>> x = so.numpy_dict()
>>> x["a"] = np.zeros((2,2))
>>> x["b"] = np.ones((2,2))
>>> x["a"]
array([[ 0.,  0.],
       [ 0.,  0.]])
>>> x["b"]
array([[ 1.,  1.],
       [ 1.,  1.]])
>>> dict.__getitem__(x, "a")
'/tmp/tmpxIxt0O'
>>> dict.__getitem__(x, "b")
'/tmp/tmpIviN4M'
>>> from sys import getrefcount as refs
>>> x = np.zeros((2,2))
>>> refs(x)
2
>>> x = so.numpy_dict()
>>> y = np.zeros((2,2))
>>> refs(y)
2
>>> x["c"] = y
>>> refs(y)
2
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...