Seite 1 von 1

Wie verändere ich recursiv den Value (v) einer Liste

Verfasst: Mittwoch 4. Dezember 2013, 09:58
von callsaender
Also, ich möchte den String in v verändern, das funktioniert wenn ich ihn direkt ausgebe aber nicht wenn ich den String v übergeben will. v ist kein String das ist klar, aber in was muss ich den String verpacken/ umwandeln damit er reinpasst?

Code: Alles auswählen


def changevalinlist(d):
  for k, v in d.iteritems():
    if isinstance(v, dict):
     changevalinlist(v)
    else: 
        # funktioniert
        print([w.replace('hallo', 'tschüs') for w in v])
        # das nicht
        v = [w.replace('hallo', 'tschüs') for w in v]
            
Hat jemand eine Idee?

Man findet überall nur Beispiel wo der Schlüssel(k) geändert wird weil das andere wohl trivial ist, ich aber nicht drauf komme. :-/

Re: Wie verändere ich recursiv den Value (v) einer Liste

Verfasst: Mittwoch 4. Dezember 2013, 10:16
von EyDu

Code: Alles auswählen

d[k] = [w.replace('hallo', 'tschüs') for w in v]
callsaender hat geschrieben:Man findet überall nur Beispiel wo der Schlüssel(k) geändert wird weil das andere wohl trivial ist, ich aber nicht drauf komme. :-/
Das glaube ich nicht, denn das ist bei einem Dictionary gar nicht möglich.

"changevalinlist" ist übrigens ein sehr seltsamer Name. Unnötige Abkürzung, hält sich nicht an PEP 8, sagt gar nichts über die Funktion aus und bekommt dann noch ein Dictionary übergeben in dem eine Liste geändert wird.

Re: Wie verändere ich recursiv den Value (v) einer Liste

Verfasst: Mittwoch 4. Dezember 2013, 10:37
von callsaender
@EyDu
- der Name der Funktion hieß 'cleanup' und nicht 'changevalinlist'
- replaced wird " gegen \"

Ich wollte nicht verwirren, weil mit dem Entfernen von Zeichen wie
'double quote " ' noch andere Probleme mit kommen.

Re: Wie verändere ich recursiv den Value (v) einer Liste

Verfasst: Mittwoch 4. Dezember 2013, 10:41
von BlackJack
@callsaender: Ergänzend zu EyDu's Anmerkungen musst Du wenn Du das Wörterbuch veränderst über eine Liste mit den Schlüssel/Wert-Paaren iterieren, also `items()` statt `iteritems()`. Wenn man über Container-Objekte verändert, während man gleichzeitig über den Inhalt iteriert, ist nicht garantiert, dass man den kompletten Inhalt in der Schleife sieht.

Um die ``print``-Anweisung gehören in Python 2 keine Klammern. Es sei denn man hat den entsprechenden `__future__`-Import der aus der Anweisung eine Funktion macht oben im Modul stehen.

Bist Du immer noch dabei JSON-P-Dateien mit ungeeigneten Mitteln zu bearbeiten? :-)

Re: Wie verändere ich recursiv den Value (v) einer Liste

Verfasst: Mittwoch 4. Dezember 2013, 12:34
von callsaender
Bist Du immer noch dabei JSON-P-Dateien mit ungeeigneten Mitteln zu bearbeiten? :-)
@BlackJack: ja :-)
.

Re: Wie verändere ich recursiv den Value (v) einer Liste

Verfasst: Mittwoch 4. Dezember 2013, 14:32
von callsaender
Da habe ich noch ein Problem

Code: Alles auswählen

d[k] = [w.replace('hallo', 'tschüs') for w in v]
d[k] enthält jetzt zwar den String aber durch das 'for w in v' werden viele kleine Listeelemente erzeugt u't' u's' u'h' u'ü' u's' .......

Ich brauche aber etwas wie:

Code: Alles auswählen

w = str(d[k])
w.replace('hallo', 'tschüs')
d[k] = w

Re: Wie verändere ich recursiv den Value (v) einer Liste

Verfasst: Mittwoch 4. Dezember 2013, 14:57
von BlackJack
@callsaender: Wenn `v` gar keine Liste von Zeichenketten ist sondern selbst eine Zeichenkette, dann lass die „list comprehension” doch einfach weg. Eine Zeichenkette ist halt auch iterierbar → die Elemente sind die einzelnen Zeichen.

Wenn Du zwischen Zeichenkette und Liste unterscheiden musst, dann musst Du genau das an der Stelle halt machen: Zeichenketten anders als Listen behandeln. Also nur bei Zeichenketten die Ersetzung durchführen und bei Listen eine neue Liste erstellen auf deren Elemente die Funktion wieder rekursiv angewendet wird.

Re: Wie verändere ich recursiv den Value (v) einer Liste

Verfasst: Mittwoch 4. Dezember 2013, 15:34
von callsaender
@BlackJack: Ich hoffe ich habe kappiert was 'list comprehension'

Code: Alles auswählen

         
        // Funktioniert 
        print d[k].replace('hallo', 'tschüs')
        // das aber nicht
        d[k] = d[k].replace('hallo', 'tschüs')
        print d[k]

Richtig wäre:
tschüs
tschüs

Aushabe:
tschüs
hallo

woran liegt es?

Re: Wie verändere ich recursiv den Value (v) einer Liste

Verfasst: Mittwoch 4. Dezember 2013, 15:47
von EyDu
Mit so kleinen Schnipseln können wird dir kaum helfen. Erstelle mal ein minimales *lauffähiges* Beispiel welches deinen Fehler produziert und poste das hier. Beim Kürzen deines Programms findest du wahscheinlich den Fehler schon selbst.

Re: Wie verändere ich recursiv den Value (v) einer Liste

Verfasst: Mittwoch 4. Dezember 2013, 16:05
von BlackJack
@callsaender: Das kann nicht sein. Wenn Du einen neuen Wert einem Schlüssel zuweist und der gleich danach nicht wieder auslesbar wäre, dann hätten Wörterbücher ein extrem heftiges Problem. Ich bin mir sicher das wäre schon mal jemandem vor Dir aufgefallen. ;-)

Re: Wie verändere ich recursiv den Value (v) einer Liste

Verfasst: Donnerstag 5. Dezember 2013, 07:20
von callsaender
@EyDu : so hier hast du ein kleines lauffähiges Beispiel

Code: Alles auswählen

# -*- coding: cp1252 -*-
import sys
import codecs
import unicodedata
import io

dic = {"a":"schlecht"}

# recursion
def my_replace(d):
  for k, v in d.iteritems():
    if isinstance(v, dict):
     my_replace(v)
    else:
        print d[k].replace('schlecht', 'gut') 
        d[k].replace('schlecht', 'gut')
        print d[k]


my_replace(dic)

Das Ergebnis ist:
gut
schlecht

Aber es müsste raus kommen
gut
gut

Re: Wie verändere ich recursiv den Value (v) einer Liste

Verfasst: Donnerstag 5. Dezember 2013, 08:13
von Hyperion
Wozu die sinnlosen Imports? Die gehören in ein Minimalbeispiel nicht rein!
callsaender hat geschrieben:
Das Ergebnis ist:
gut
schlecht

Aber es müsste raus kommen
gut
gut
Nö!
Mal als Tipp:

Code: Alles auswählen

d = {"a": "schlecht"}

d["a"]
'schlecht'

'schlecht'.replace('schlecht', 'gut')
'gut'

d['a'].replace('schlecht', 'gut')
'gut'

d
{'a': 'schlecht'}
Du holst Dir den zu einem Schlüssel gehörigen Wert *aus* dem Dictionary und führst ``replace`` auf diesem aus. Du ersetzt aber eben *nicht* den Wert *im* Dictionary ;-)

Das geht per Zuweisung:

Code: Alles auswählen

d["a"] = "gut"

Re: Wie verändere ich recursiv den Value (v) einer Liste

Verfasst: Donnerstag 5. Dezember 2013, 08:41
von BlackJack
@callsaender: Und zum drölftausendsten mal: Nicht über eine Datenstruktur iterieren *und* sie verändern. Undefiniertes Verhalten. Böse.

Re: Wie verändere ich recursiv den Value (v) einer Liste

Verfasst: Donnerstag 5. Dezember 2013, 09:14
von callsaender
@Hyperion: Danke funzt

@BlackJack: Ich suche noch eine Lösung für das Problem !

Code: Alles auswählen

if language != 'de':
    for de_parent in tree.findall('.//de/..'):
        de_parent.remove(de_parent.find('de'))
bei der XML Geschichte habe ich ja schon gemacht. Bei der Pyhtonliste funktioniert das nicht so einfach! ???

Re: Wie verändere ich recursiv den Value (v) einer Liste

Verfasst: Donnerstag 5. Dezember 2013, 09:55
von BlackJack
@callsaender: Welches Problem? Welche Liste?

Re: Wie verändere ich recursiv den Value (v) einer Liste

Verfasst: Donnerstag 5. Dezember 2013, 10:16
von callsaender
@BlackJack: wie würdest du das machen wenn nicht mit iteritems() oder iter() was man nicht einfach
hier ersetzen kann oder .findall() was ich in dieser "Datenstruktur" noch nicht hin bekommen habe ??
Und zum drölftausendsten mal: Nicht über eine Datenstruktur iterieren *und* sie verändern. Undefiniertes Verhalten. Böse.
Python Datenstruktur meinte ich !

z.B

d = {"a":{"b":{"c":"hello"}}}

wenn ich z.B. hello in hallo ändern möchte

Code: Alles auswählen

def my_replace(d):
  for k, v in d.iteritems():
    if isinstance(v, dict):
     my_replace(v)
    else:
       #change value of d[k]

Re: Wie verändere ich recursiv den Value (v) einer Liste

Verfasst: Donnerstag 5. Dezember 2013, 10:24
von BlackJack
@callsaender: Welche Methode man statt `iteritems()` verwenden muss habe ich hier schon geschrieben.

Re: Wie verändere ich recursiv den Value (v) einer Liste

Verfasst: Donnerstag 5. Dezember 2013, 11:57
von callsaender
@BlackJack:
Ich hatte items() schon mal aus probiert und bekam eine Fehlermeldung die aber wo anders her kam, wie sich jetzt rausgestellt hat. Und ich verwende jetzt selbstverständlich 'item' wenn es dich beruhigt ;-)

@all
Es gibt das Kommentierungzeichen '#' in Python. In C kann man mehrere Zeilen gleichzeitig Kommentieren mit /* */ gibt es in Python ewas ähnliches ?

Hintergrung: Ich habe für den Rest des Projekts (nicht in Python geschrieben) sowas wie JavaDoc das die Kommentare raus filtert und in eine html Doku fasst.

Re: Wie verändere ich recursiv den Value (v) einer Liste

Verfasst: Donnerstag 5. Dezember 2013, 12:36
von BlackJack
@callsaender: Nein in Python gibt es nur # für Kommentare. Jeder brauchbare Editor kann damit aber auch Blöcke aus/einkommentieren. Für generierte Dokumentation wird in Python üblicherweise DocStrings verwendet. Die meisten Systeme erkennen auch noch spezielle Kommentare. Sphinx zum Beispiel wenn der Kommentar mit #: anfängt. Sphinx ist das Dokumentationswerkzeug mit dem unter anderem die Python-Dokumentation erstellt wird.