Domanda

Sono stato incaricato con la creazione di un database SKU flat-file per l'utilizzo su dispositivi embedded con memoria limitata e la velocità del processore.

In sostanza i dati ho bisogno di memorizzare è costituito dai seguenti:

SKU Descrizione Posizione Prezzo Quantità

Il file sarà composto da diversi milioni di dischi.

Le considerazioni più importanti sono lo spazio di archiviazione e il tempo di recupero. Records avranno solo bisogno di essere recuperato da SKU e sarà di sola lettura, quindi il file possono essere ordinati per SKU.

Vorrei accedere a questi dati con Python. Quindi le mie domande si riduce a questo.

Ci sono le librerie Python esistenti in grado di fornire questa funzionalità per me, o devo a rotolare il mio?

Se la risposta si riduce a rotolare il mio, Qualcuno ha un suggerimento, o buone referenze per farlo?

È stato utile?

Soluzione

Come su SQLite con Python? Ha un po 'più del necessario, ma è software standard e ben collaudato.

Altri suggerimenti

Il vecchio modo sarebbe quello di utilizzare una tabella di dati semplice chiave / valore come modulo gdbm. Python viene fornito con supporto per questo, ma non è costruito nella installazione di Python di default sulla mia macchina.

In generale, utilizzare SQLite. Come altri hanno scritto, che viene fornita di serie con Python, ed è usato in molti sistemi embedded già.

Se i record sono a lunghezza fissa, è possibile utilizzare il modulo bisect. La dimensione del file / la dimensione del record indica il numero di record nel file. La ricerca bisect farà un O (log n ()) di ricerca nel file, e avrete bisogno di scrivere un adattatore per verificare l'uguaglianza. Anche se non ho provato, ecco un abbozzo:

import bisect

RECORD_SIZE = 50

class MatchFirst10Chars(object):
    def __init__(self, word):
        self.word = word
    def __lt__(self, other):
        return self.word < other[:10]

class FileLookup(object):
    def __init__(self, f):
        self.f = f
        f.seek(0, 2)
        self.size = f.tell() // RECORD_SIZE
    def __len__(self):
        return self.size

    def __getitem__(self, i):
        self.f.seek(i*RECORD_SIZE)
        return self.f.read(RECORD_SIZE)


SKU = "123-56-89 "
f = open("data_file")
fl = FileLookup(f)
i = bisect.bisect(fl, MatchFirst10Chars(SKU))

Si potrebbe inoltre gzip il file e cercare su un file gzip'ped, ma questo è un compromesso per lo spazio in funzione del tempo che dovrete mettere alla prova.

Mi permetto di suggerire CDB ? (Binding Python:. python-CDB )

E 'un formato utilizzato per i dati di sola lettura, come si dispone; è fondamentalmente 256 tabelle hash giganti, ciascuno in grado di avere un diverso numero di bucket. La cosa bella di CDB è che il file non ha bisogno di essere caricato in memoria; è strutturato in un modo che si può fare ricerche semplicemente mmaping nei bit necessari.

Il CDB spec è una buona lettura, anche perché le linee sono formattato per creare un margine destro uniforme. :-D

Come su HDF ? Se non avete bisogno di SQL e richiedono un rapido accesso ai dati, non c'è niente di più veloce ... in Python ... per i dati numerici o strutturati.

Date un'occhiata alla DatabaseInterfaces sezione sulla Python wiki. E 'completo. Ci sono un paio di opzioni Python "puri" di cui (come SnakeSQL ), che sono un po 'più bello da distribuire. E, naturalmente, c'è sempre Berkeley DB e simili, che sono super magra & crudo.

Onestamente, SQLite probabilmente funzionerà bene per voi. Se avete veramente bisogno di eek fuori più prestazioni, allora si sarebbe essere guardando un formato basato su record come BDB.

Una soluzione semplice è cPickle . È inoltre possibile trovare domande simili su SO.

Una variazione della risposta di Andrew Dalke (in modo da poter ancora utilizzare la ricerca binaria per individuare la SKU rapidamente) che possono ridurre i requisiti di spazio sarebbe quello di avere dischi fissi di dimensioni all'inizio del file (uno per SKU) e poi tutto le descrizioni e le posizioni (come null terminata stringhe dicono)

Si arriva a risparmiare spazio non dovendo pad le posizioni e le descrizioni a lunghezza fissa. Inoltre è possibile risparmiare spazio se ci sono un sacco di luoghi duplicati

Ecco un esempio: dire che hai

SKU         16 bytes
Description Variable length
Location    Variable length
Price       4 bytes (up to $42949672.95)
Quantity    4 bytes (up to 4294967295)



 offset          SKU        desc_off   loc_off      Price      Quantity
0x00000000 SKU0000000000001 0x01f78a40 0x01f78a47  0x000003e8  0x000f4240
0x00000020 SKU0000000000002 0x01f78a53 0x01f78a59    ...
...
... # 999998 more records
...
0x01f78a40 Widget\x00
0x01f78a47 Head office\x00
0x01f78a53 Table\x00
0x01f78a59 Warehouse\x00
Autorizzato sotto: CC-BY-SA insieme a attribuzione
Non affiliato a StackOverflow
scroll top