CSV-Export

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
snowflake
User
Beiträge: 93
Registriert: Mittwoch 9. November 2016, 15:46

Guten Morgen zusammen,

ich habe hier eine Funktion mit der ich eine CSV-Datei erstelle. Funktioniert auch gut, allerdings wenn Sonderzeichen wie PI kommen, wird eine Fehlermeldung ausgegeben.

Code: Alles auswählen

   def Notizenexport():

        dateiname = asksaveasfilename(filetypes = (("csv", "*.csv"), ("Alle Dateien", "*.*")), defaultextension = ".csv", title = "CSV-Datei speichern")
        
        if dateiname == "":
            return
        
        writer = csv.writer(open(dateiname, "w"), delimiter = ",")
        writer.writerow(lstNotizfelder)
        listOfEntriesInTreeView = Notiztree.get_children()

        liste = []
        text = ""
        for i in listOfEntriesInTreeView:
            zuordnung = []
            for j in range(0, len(lstNotizfelder)):
                text = str(Notiztree.item(i)['values'][j]).replace("\n", " ") 
                zuordnung.append(text)
            liste.append(zuordnung)
        writer.writerows(liste)
Fehlermeldung: 'UnicodeEncodeError: 'charmap' codec can't encode character '\u03c0' in position 22: character maps to <undefined>'

Das liegt mit dem PI-Zeichen zusammen. Habe auch schon versucht, das Problem mit encoding = "utf-8" zu lösen, hat nur leider nicht funktioniert. Hat jemand eine Idee, wie ich das Problem lösen kann?

Viele Grüße und vielen Dank.

snowflake
Benutzeravatar
__blackjack__
User
Beiträge: 13004
Registriert: Samstag 2. Juni 2018, 10:21
Wohnort: 127.0.0.1
Kontaktdaten:

@snowflake: Wie sieht denn der komplette Traceback aus? Also wo tritt diese Ausnahme denn genau auf?

Und was heisst „mit encoding = "utf-8" zu lösen“ konkret? Wo hast Du das hingeschrieben? Und was funktionierte dann nicht? Die gleiche Ausnahme kann das dann ja nicht gewesen sein.

Warum ist `Notizenexport()` eingerückt? Das ist keine Methode, dafür fehlt das `self`-Argument und als Funktion sollte es aber direkt in der ersten Spalte im Texteditor anfangen.

Die Funktion greift auf `lstNotizfelder` und `Notiztree` zu ohne das die als Argumente übergeben werden. Das sollte nicht sein.

Falls das `lst` für `list` stehen soll: Weg damit. In Namen gehören weder kryptische Abkürzungen, noch Grunddatentypen. Das gilt auch für `listOfEntriesInTreeView`. Zudem halten sich die Namensschreibweisen nicht an die üblichen Konventionen: klein_mit_unterstrichen für alles ausser Konstanten (KOMPLETT_GROSS) und Klassen (MixedCase).

`i` in einer Schleife für etwas anderes als ganze Zahlen zu verwenden ist eine ganz schlechte Idee. Ebenso ist `liste` ein viel zu generischer Name. Namen sollen dem Leser vermitteln was der Wert der dahinter steht bedeutet, und nicht zum Rätselraten zwingen. Der Leser will ja nicht wissen dass das eine Liste ist, sondern was die Werte darin für eine Bedeutung im Programm haben.

Dateien die man öffnet, sollte man auch wieder schliessen, und sich nicht darauf verlassen, dass das irgendwann von selbst passiert. In dem Zusammenhang ist die ``with``-Anweisung nützlich.

Die Zuweisung an `text` vor der Schleife ist sinnlos und kann ersatzlos wegfallen. Die Variable insgesamt ist nicht wirklich sinnvoll.

Die innere Schleife ist in Python ein „anti pattern“. Man kann in Python direkt über die Elemente von Sequenzen iterieren, ohne den Umweg über einen Index. Das ist hier ja nur nötig weil in jedem inneren Schleifendurchlauf immer wieder `Notiztree.item()` aufgerufen wird, mit dem gleichen Wert für `i`, statt das *einmal* *vor* der inneren Schleife zu machen.
“Most people find the concept of programming obvious, but the doing impossible.” — Alan J. Perlis
snowflake
User
Beiträge: 93
Registriert: Mittwoch 9. November 2016, 15:46

Hallo __blackjack__,

hier die komplette Fehlermeldung:

Exception in Tkinter callback
Traceback (most recent call last):
File "C:\Users\snowflake\AppData\Local\Programs\Python\Python35\lib\tkinter\__init__.py", line 1549, in __call__
return self.func(*args)
File "Notizen.py", line 57, in Notizenexport
writer.writerows(liste)
File "C:\Users\snowflake\AppData\Local\Programs\Python\Python35\lib\encodings\cp1252.py", line 19, in encode
return codecs.charmap_encode(input,self.errors,encoding_table)[0]
UnicodeEncodeError: 'charmap' codec can't encode character '\u03c0' in position 109: character maps to <undefined>


Der Versuch mit encoding sieht so aus:

Code: Alles auswählen

writer = csv.writer(open(dateiname, "w"), delimiter = ",",  encoding = "utf-8")
Die Fehlermeldung war die Gleiche.

Vielen Dank für Deine Rückmeldung.

snowflake
Benutzeravatar
__blackjack__
User
Beiträge: 13004
Registriert: Samstag 2. Juni 2018, 10:21
Wohnort: 127.0.0.1
Kontaktdaten:

@snowflake: Das kann nicht die gleiche Fehlermeldung gegeben haben. Bei Der Zeile hättest Du einen `TypeError` bekommen weil dort kein `encoding` stehen darf.
“Most people find the concept of programming obvious, but the doing impossible.” — Alan J. Perlis
snowflake
User
Beiträge: 93
Registriert: Mittwoch 9. November 2016, 15:46

Hallo __blackjack__,

sorry, ich habe vom falschen Skript die Fehlermeldung kopiert. Das ist die Meldung die erscheint, wenn ich die Zeile wie oben beschrieben, abändere.

Exception in Tkinter callback
Traceback (most recent call last):
File "C:\Users\snowflake\AppData\Local\Programs\Python\Python35\lib\tkinter\__init__.py", line 1549, in __call__
return self.func(*args)
File "Notizen.py", line 45, in Notizenexport
writer = csv.writer(open(dateiname, "w"), delimiter = ",", encoding="utf-8")
TypeError: 'encoding' is an invalid keyword argument for this function


Viele Grüße

snowflake
__deets__
User
Beiträge: 14494
Registriert: Mittwoch 14. Oktober 2015, 14:29

Na Fehlermeldung ist doch recht klar. Das encoding muss in die open-Funktion. Bei Python3! Sonst musst du mit dem codecs-Modul arbeiten.
snowflake
User
Beiträge: 93
Registriert: Mittwoch 9. November 2016, 15:46

@__deets_: Das dass mit dem 'encoding' nicht funktioniert habe ich oben ja schon geschrieben.

Auf die Idee das 'encoding' in die Open-Funktion zu schreiben bin ich nicht gekommen. Das funktioniert jetzt auch.


Vielen Dank an Euch.

snowflake
Antworten