executemany()

Wenn du dir nicht sicher bist, in welchem der anderen Foren du die Frage stellen sollst, dann bist du hier im Forum für allgemeine Fragen sicher richtig.
Antworten
_Sebastian_
User
Beiträge: 21
Registriert: Sonntag 16. April 2006, 12:48

Hallo,

ich habe ein Problem mit executemany() von pysqlite.
Ein direkt aus dem Usage-Guide entnommenes Beispiel funktioniert:

Code: Alles auswählen

from pysqlite2 import dbapi2 as sqlite

con = sqlite.connect("test")

cur = con.cursor()

newPeople = (
    ('Lebed'       , 53),
    ('Zhirinovsky' , 57),
  )

cur.executemany("insert into people (name_last, age) values (?, ?)", newPeople) 

# The changes will not be saved unless the transaction is committed explicitly:
con.commit()
Ändere ich das aber ein wenig ab, bekomme ich die Fehlermeldung
Traceback (most recent call last):
File "test.py", line 12, in ?
cur.executemany("insert into people (name_last) values (?)", newPeople)
pysqlite2.dbapi2.ProgrammingError: Incorrect number of bindings supplied. The current statement uses 1, and there are 5 supplied.
Mein geänderter Code:

Code: Alles auswählen

from pysqlite2 import dbapi2 as sqlite

con = sqlite.connect("test")

cur = con.cursor()

newPeople = (
    ('name1'),
    ('name2'),
  )

cur.executemany("insert into people (name_last) values (?)", newPeople) 

# The changes will not be saved unless the transaction is committed explicitly:
con.commit()
Woran liegt das? Gibt es vielleicht irgendwo eine genaue Referenz, was ich executemany() als 2. Parameter übergeben darf?
Zuletzt geändert von _Sebastian_ am Donnerstag 3. August 2006, 14:21, insgesamt 1-mal geändert.
Benutzeravatar
DatenMetzgerX
User
Beiträge: 398
Registriert: Freitag 28. April 2006, 06:28
Wohnort: Zürich Seebach (CH)

Code: Alles auswählen

from pysqlite2 import dbapi2 as sqlite

con = sqlite.connect("mydb")

cur = con.cursor()

newPeople = ({'name_last': 'Lebed', 'age': 53},
    {'name_last':'Zhirinovsky' ,'age':  57}
  )

cur.executemany("insert into people (name_last, age) values (?, ?)", newPeople)

# The changes will not be saved unless the transaction is committed explicitly:
con.commit()
sollte so gehen, nicht getestet
_Sebastian_
User
Beiträge: 21
Registriert: Sonntag 16. April 2006, 12:48

Aber dein Code fügt doch genau das gleiche in die DB ein, wie das Beispiel aus dem Usage Guide, oder?

Was ich eigentlich wissen wollte:
Ich habe ein Tupel/Liste, z.b. testlist = ['name1', 'name2'] und will das executemany() übergeben - aber warum funktioniert das nicht?
BlackJack

`executemany()` braucht als zweiten Parameter ein "iterable" über Sequenzen. Du hast in Deinem zweiten Versuch aber kein Tupel mit Tupeln übergeben sondern nur ein Tupel mit zwei Zeichenketten! Die Klammern "machen" keine Tupel, sondern die Kommata. Ein Tupel mit einem Element muss also so aussehen: ('hallo',). Man beachte das Komma!
_Sebastian_
User
Beiträge: 21
Registriert: Sonntag 16. April 2006, 12:48

Bin mir nicht ganz sicher, ob ich deine Erklärung verstanden habe :)
Läuft es auf ein verschachtelte Arrays hinaus?
BlackJack

Sozusagen. Du kannst aber auch Tupel nehmen. Du musst sie nur richtig deklarieren:

Code: Alles auswählen

n [22]: type( ('hallo') )
Out[22]: <type 'str'>

In [23]: type( ('hallo',) )
Out[23]: <type 'tuple'>
Das Komma fehlte in Deinem Beispiel das nicht funktionierte. Ohne das Komma hast Du nur ein Tupel mit zwei Zeichenketten und kein Tupel mit zwei Tupeln die jeweils eine Zeichenkette enthalten.
Joghurt
User
Beiträge: 877
Registriert: Dienstag 15. Februar 2005, 15:07

BlackJack hat geschrieben:Ohne das Komma hast Du nur ein Tupel mit zwei Zeichenketten und kein Tupel mit zwei Tupeln die jeweils eine Zeichenkette enthalten.
Und deshalb wurde auch über die einzelnen Buchstaben des Strings iteriert. Daher kommt auch das "there are 5 supplied.", denn "demo1" hat 5 Buchstaben.

Code: Alles auswählen

>>> for x in ("Hallo"): print x
H
a
l
l
o
>>> for x in ("Hallo",): print x
Hallo
_Sebastian_
User
Beiträge: 21
Registriert: Sonntag 16. April 2006, 12:48

In der Tat, jetzt funktionierts und verstanden habe ich es auch :-)

Vielen Dank BlackJack und Joghurt
Antworten