db = sqlite.connect("test.sqlite")
res = db.execute("select * from table")
Przy iteracji otrzymuję listy odpowiadające wierszom.
for row in res:
print row
Mogę uzyskać nazwy kolumn
col_name_list = [tuple[0] for tuple in res.description]
Ale czy jest jakaś funkcja lub ustawienie do pobierania słowników zamiast listy?
{'col1': 'value', 'col2': 'value'}
czy muszę zrobić sam?
python
sql
sqlite
dictionary
dataformat
Meloun
źródło
źródło
Odpowiedzi:
Możesz użyć row_factory , jak w przykładzie w dokumentach:
lub postępuj zgodnie z radą podaną zaraz po tym przykładzie w dokumentacji:
źródło
SELECT 1 AS "dog[cat]"
Wtedycursor
nie będą miały poprawnego opisu do utworzenia dykta.connection.row_factory = sqlite3.Row
i próbowałem,connection.row_factory = dict_factory
jak pokazano, alecur.fetchall()
nadal wyświetla mi listę krotek - masz pojęcie, dlaczego to nie działa?collections.namedtuple
. Kiedy używamcur.fetchmany()
, otrzymuję wpisy takie jak<sqlite3.Row object at 0x...>
.Pomyślałem, że odpowiem na to pytanie, chociaż odpowiedź jest częściowo wymieniona zarówno w odpowiedziach Adama Schmidega, jak i Alexa Martellego. Aby inni tacy jak ja, którzy mają to samo pytanie, mogli łatwo znaleźć odpowiedź.
źródło
fetchall()
wydaje się zwracaćsqlite3.Row
obiekty. Jednakże mogą one zostać przekształcone do słownika po prostu za pomocądict()
:result = [dict(row) for row in c.fetchall()]
.Nawet używając klasy sqlite3.Row - nadal nie możesz używać formatowania ciągów w postaci:
Aby to obejść, używam funkcji pomocniczej, która pobiera wiersz i konwertuje go na słownik. Używam tego tylko wtedy, gdy obiekt słownika jest lepszy od obiektu Row (np. W przypadku formatowania ciągów, gdzie obiekt Row nie obsługuje również natywnie interfejsu API słownika). Ale we wszystkich innych przypadkach używaj obiektu Row.
źródło
print "%(id)i - %(name)s: %(value)s" % dict(row)
Po połączeniu się z SQLite:
con = sqlite3.connect(.....)
wystarczy uruchomić:Voila!
źródło
Od PEP 249 :
Więc tak, zrób to sam.
źródło
Krótsza wersja:
źródło
Najszybciej w moich testach:
vs:
Ty decydujesz :)
źródło
Jak wspomniano w odpowiedzi @ gandalfa, trzeba użyć
conn.row_factory = sqlite3.Row
, ale wyniki nie są bezpośrednio słownikami. Wdict
ostatniej pętli trzeba dodać dodatkowe „rzutowanie” :źródło
Podobne jak wyżej wymienione rozwiązania, ale najbardziej kompaktowe:
źródło
db.row_factory = sqlite3.Row
nie zadziałała dla mnie (ponieważ spowodowała JSON TypeError)Myślę, że byłeś na dobrej drodze. Utrzymajmy to bardzo prosto i dokończmy to, co próbowałeś zrobić:
Wadą jest to
.fetchall()
, że jest to morderstwo w zużyciu pamięci , jeśli twój stół jest bardzo duży. Ale w przypadku trywialnych aplikacji zajmujących się zaledwie kilkoma tysiącami wierszy tekstu i kolumn liczbowych to proste podejście jest wystarczające.W przypadku poważnych spraw powinieneś zajrzeć do fabryk rzędowych, zgodnie z propozycjami w wielu innych odpowiedziach.
źródło
Lub możesz przekonwertować sqlite3.Rows na słownik w następujący sposób. To da słownik z listą dla każdego wiersza.
źródło
Ogólna alternatywa, wykorzystująca tylko trzy linie
Ale jeśli twoje zapytanie nic nie zwróci, spowoduje błąd. W tym przypadku...
lub
źródło
Wynik jest zdecydowanie prawdziwy, ale nie znam najlepszego.
źródło
Słowniki w Pythonie zapewniają dowolny dostęp do swoich elementów. Tak więc każdy słownik z „nazwami”, chociaż z jednej strony może być pouczający (czyli jakie są nazwy pól) „anuluje porządkowanie” pól, co może być niepożądane.
Najlepszym podejściem jest umieszczenie nazwisk na osobnej liście, a następnie, w razie potrzeby, samodzielne połączenie ich z wynikami.
Pamiętaj również, że we wszystkich podejściach nazwy są nazwami podanymi w zapytaniu, a nie nazwami w bazie danych. Wyjątkiem jest
SELECT * FROM
Jeśli Twoim jedynym zmartwieniem jest uzyskanie wyników za pomocą słownika, zdecydowanie użyj
conn.row_factory = sqlite3.Row
(już podano w innej odpowiedzi).źródło