Wert von Liste mit seinem Index multiplizieren

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.
elNino
User
Beiträge: 6
Registriert: Dienstag 10. Dezember 2013, 18:30

Ich hab hier ein Problem :? Ich will einen Algoritmus schreiben in dem eine Liste eingelesen wird und dann jeder Wert der Liste mit seinem Index multipliziert wird. Also z.b. aus [1,2,3] wird [0,2,6].
Habe jetzt lange überlegt und bei meinem Algoritmus wird leider immer [[]] ausgegeben. Wo ist denn mein Fehler? :K

Code: Alles auswählen

def MultiIndex (Liste):
    Index = 0
    ListeNeu = []
    while Liste != []:      # Bis die eingegebene Liste leer ist tue folgendes:
     b=Liste[Index]        # Nimmt einen Wert von der Stelle "Index"aus der Liste und schreibe ihn in b
     del Liste[Index]       # Löscht den betrachteten Wert aus der Liste
     c=Index * b            # Multipliziert den Wert mit seinem Index
     ListeNeu.append(c)  # Füge den Multiplizierten Wert zu einer neuen Liste hinzu
     Index = Index+1       
    return ListeNeu

Liste = []
Ziffer = input("Geben Sie eine Liste von Ziffer ein die mit einem Komma getrennt sind: ").split(",")
Liste.append(Ziffer)
Liste =  MultiIndex (Liste)
print (Liste)
derdon
User
Beiträge: 1316
Registriert: Freitag 24. Oktober 2008, 14:32

Code: Alles auswählen

>>> l = [1,2,3]
>>> [i * elem for i, elem in enumerate(l)]
[0, 2, 6]
fertig :)
BlackJack

@elNino: Dein erstes Problem ist schon die Liste die Du der Funktion übergibst. Schau Dir die mal an. Die enthält als einziges Argument eine weitere Liste. Und die wiederum enthält *Zeichenketten* und keine Zahlen.
Benutzeravatar
/me
User
Beiträge: 3554
Registriert: Donnerstag 25. Juni 2009, 14:40
Wohnort: Bonn

@elNino: Bitte schau dir auch mal den Style Guide for Python Code an. Du hast einige Dinge in deinem Code, die ihn für den etwas erfahreneren Python-Entwickler schwer lesbar machen.

Empfohlen werden im Style Guide unter anderem
  • Funktions- und Variablennamen in Kleinbuchstaben mit Unterstrichen
  • Leerzeichen rund um Operatoren und Gleichheitszeichen (allerdings mit kontextabhängigen Ausnahmen)
  • Kein Setzen von Leerzeichen vor einer öffnenden Klammer
  • Eine einheitliche Einrücktiefe von 4 Leerzeichen pro Ebene
Es kann sein, dass manche Teams sich aus historischen Gründen auf andere Standards geeinigt haben. In deinem Fall hast du aber nicht mal Konsistenz innerhalb auch nur eines kleinen Codeabschnitts.
Sirius3
User
Beiträge: 17710
Registriert: Sonntag 21. Oktober 2012, 17:20

@elNino: Dein Problem ist, dass null mal eine Liste eine leere Liste gibt:

Code: Alles auswählen

>>> ['1', '2', '3'] * 0
[]
Deine Funktion hat unerwartete Nebeneffekte. Wenn ich eine Liste als Argument übergebe und eine andere Liste zurückbekomme, erwarte ich, dass sich die Liste die ich übergebe nicht ändert. Das tut sie bei Dir.
elNino
User
Beiträge: 6
Registriert: Dienstag 10. Dezember 2013, 18:30

@ derdon
Ja also das sieht ja so recht einfach aus wie du es gemacht hast. Aber bei mir funktioniert das nicht weil l ja garnicht definiert ist bei dir. Ich versteh deinen Ansatz nicht richtig!


@BlackJack
Was währe denn eine gute Methode um eine Liste vom Benutzer eingeben zu lassen? Dabei ist mir eigentlich egal, ob er die Elemente der Liste einzeln oder hinterneinander mit komma getrennt eingibt.


@ /me
Danke für die Style tipps. Werde sie Zukünftig berücksichtigen.


@ Sirius
In welcher Zeile multipliziere ich denn meine liste mit 0? Ich multipliziere doch in Zeile 7 nur ein Element der Liste mal 0, nähmlich das erste. Beim nächsten durchgang der Schleife wird ja dann das nächste Element mit 1 multipliziert. Also so war es jedenfalls gedacht.
Benutzeravatar
Hyperion
Moderator
Beiträge: 7478
Registriert: Freitag 4. August 2006, 14:56
Wohnort: Hamburg
Kontaktdaten:

elNino hat geschrieben: @ Sirius
In welcher Zeile multipliziere ich denn meine liste mit 0? Ich multipliziere doch in Zeile 7 nur ein Element der Liste mal 0, nähmlich das erste. Beim nächsten durchgang der Schleife wird ja dann das nächste Element mit 1 multipliziert. Also so war es jedenfalls gedacht.
Lass Dir mal nach Zeile 14 Deine ``Liste`` ausgeben ;-) Die ist nämlich anders aufgebaut, als Du es erwartest! BlackJack schrieb Dir das bereits.

Zur Lösung von derdon:
Die Funktion ``enumerate`` generiert Dir einen Index zu jedem Element einer Liste. Du kannst das auch in einer ``for``-Schleife nachstellen:

Code: Alles auswählen

for index, item in enumerate(eine_liste):
    print(index, item, index * item)
Du könntest das bei Dir nach Zeile 13 einbauen z.B.
encoding_kapiert = all(verstehen(lesen(info)) for info in (Leonidas Folien, Blog, Folien & Text inkl. Python3, utf-8 everywhere))
assert encoding_kapiert
derdon
User
Beiträge: 1316
Registriert: Freitag 24. Oktober 2008, 14:32

elNino hat geschrieben:@ derdon
Ja also das sieht ja so recht einfach aus wie du es gemacht hast. Aber bei mir funktioniert das nicht weil l ja garnicht definiert ist bei dir. Ich versteh deinen Ansatz nicht richtig!
l ist bei dir doch definiert, nur hat es einen anderen Namen: Liste. So heißt der Parameter deiner Funktion. Nachdem du die Antwort von Hyperion gelesen hast, solltest du ja auch nicht sagen „Das geht bei mir aber gar nicht, weil eine_liste gar nicht definiert ist bei mir!”.

Und auch bei mir ist l definiert, direkt in der Zeile dadrüber von meinem Schnipsel.
elNino
User
Beiträge: 6
Registriert: Dienstag 10. Dezember 2013, 18:30

Ich habe es geschafft eine Funktion zu schreiben die mir es erlaubt Listen einzugeben indem ich jedes Element der Liste einzeln eingebe. Allerdings finde ich diese Lösung nicht sehr Elegant. Gibt es da einen einfacheren Weg Listen Einzugeben?

Code: Alles auswählen

def eingabe(a):
    liste =[]
    eingabe = [0]
    try:
        while eingabe != []:
            eingabe = int(input("Geben sie eine Zahl für die Liste ein: "))
            liste.append(eingabe)
    except:
        print (liste)
    return (liste)

print ("Liste 1")
liste1 = eingabe(liste1)
print ("Liste 2")
liste2 = eingabe(liste2)
ViciousKitty
User
Beiträge: 8
Registriert: Dienstag 17. Dezember 2013, 13:05

Bin zwar Anfängerin, aber hattest du da nicht schon ne Lösung?

Code: Alles auswählen

x = raw_input()
type(x.split(','))
Also schaut so aus als ob dir split ne Liste liefert.

Aber achtung, das sind dann alles Strings wie schon erwähnt wurde glaube ich

Code: Alles auswählen

type(x.split(',')[0])
elNino
User
Beiträge: 6
Registriert: Dienstag 10. Dezember 2013, 18:30

BlackJack meinte : Dein erstes Problem ist schon die Liste die Du der Funktion übergibst. Schau Dir die mal an. Die enthält als einziges Argument eine weitere Liste. Und die wiederum enthält *Zeichenketten* und keine Zahlen.

deswegen hatte ich überlegt wie man sonst eine liste eingeben lassen könnte. Ich habe deinen Vorschlag mal ausprobiert @Kitty.

Code: Alles auswählen

x = raw_input("Gib eine Liste ein: ")
type(x.split(',')[0])
print (type(x))
print (x)
Gib eine Liste ein: 1,2,3,4
<class 'str'>
1,2,3,4

Wenn ich es richtig verstehe ist die das ein String bei der Eingabe. Ich bräuchte aber eineListe als Typ.
ViciousKitty
User
Beiträge: 8
Registriert: Dienstag 17. Dezember 2013, 13:05

Das ist ja ne Liste, mach mal print type(x)
Nur die Elemente der Liste sind Strings, aber da hilft ja int()

Aja, ich hatte raw_input verwendet (stand so in nem Lehrbuch).

Damit das bei input() noch ne Liste wird, musst du anscheinend eckige Klammern noch außen rum basteln
BlackJack

@elNino: Meide `input()`. Damit kann der Benutzer nahezu beliebigen Python-Code eingeben der dann ausgeführt wird. Das `int()` macht bei `input()` auch nicht wirklich Sinn. Genausowenig wie `eingabe` am Anfang an eine Liste mit einer 0 drin zu binden oder auf ``!= []`` zu prüfen weil das immer wahr ist.

Wie ViciousKitty schon sagte: Zeichenkette eingeben lassen, an Trennzeichen zu einer Liste mit Zeichenketten aufteilen lassen, und dann mit `int()` die einzelnen Elemente in Zahlen umwandeln.

Die `map()`-Funktion ist an der Stelle vielleicht ganz nützlich. (Oder `itertools.imap()`.)
elNino
User
Beiträge: 6
Registriert: Dienstag 10. Dezember 2013, 18:30

Ich habe eine Lösung gefunden. Das funktioniert gut:

Code: Alles auswählen

x = input("Gib eine Liste ein: ")
x=[int(i) for i in x.split(',')]
print (type (x))
print (x)
Gib eine Liste ein: 1,2,3,4
<class 'list'>
[1, 2, 3, 4]

aber danke für den Tip mit der map() Funktion. Hab mir grad mal angeschaut was die so macht. Hab aber leider keine Lösung für mein Problem damit gefunden grad. Aber ist sicherlich nützlich zu wissen das es diese Funktion gibt.
Ich würde aber trotzdem gerne wissen wie das ohne input fünktionieren würde :K
ViciousKitty
User
Beiträge: 8
Registriert: Dienstag 17. Dezember 2013, 13:05

Oki, das klappt bei mir aber nur unter 3.x
C:\Python27>py -2
Python 2.7.5 (default, May 15 2013, 22:43:36) [MSC v.1500 32 bit (Intel)] on win32
Type "help", "copyright", "credits" or "license" for more information.
>>> exec(open('liste.py').read())
Gib eine Liste ein: 1, 2, 3, 4
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
File "<string>", line 2, in <module>
AttributeError: 'tuple' object has no attribute 'split'
>>>

Oki, klappt doch - aber nur wenn man die Liste mit Anführungszeichen angibt, damit er die split Methode findet
Benutzeravatar
cofi
Python-Forum Veteran
Beiträge: 4432
Registriert: Sonntag 30. März 2008, 04:16
Wohnort: RGFybXN0YWR0

Die list comprehension sieht mit `map` so aus:

Code: Alles auswählen

x = map(int, x.split('.')
Prinzipiell hat man mit `map` keinen Vorteil gegenueber einer List Comprehension, insofern brauchst du nicht tiefer zu graben ;) Sich mit Higher Order Funktionen wie `map` auseinanderzusetzen ist aber nie falsch :)

@ViciousKitty: Das ist genau das was BlackJack meinte, als er sagte "Meide `input()`." ;) (Das gilt natuerlich nur fuer Python2)
Da du scheinbar gerne mit `type` herumspielst, schau dir doch mal an, was `x` nach der 1. Zeile gebunden ist und was fuer einen Typ das hat.
ViciousKitty
User
Beiträge: 8
Registriert: Dienstag 17. Dezember 2013, 13:05

cofi hat geschrieben:Die list comprehension sieht mit `map` so aus:

Code: Alles auswählen

x = map(int, x.split('.')
Prinzipiell hat man mit `map` keinen Vorteil gegenueber einer List Comprehension, insofern brauchst du nicht tiefer zu graben ;) Sich mit Higher Order Funktionen wie `map` auseinanderzusetzen ist aber nie falsch :)

@ViciousKitty: Das ist genau das was BlackJack meinte, als er sagte "Meide `input()`." ;) (Das gilt natuerlich nur fuer Python2)
Da du scheinbar gerne mit `type` herumspielst, schau dir doch mal an, was `x` nach der 1. Zeile gebunden ist und was fuer einen Typ das hat.
Scheinbar ist richtig^^, ich versuche nur die Sachen zu verstehen.
Da kommt dann ein String. Aber überrascht mich jetzt nicht, wenn ich es mit einem String füttere?
elNino
User
Beiträge: 6
Registriert: Dienstag 10. Dezember 2013, 18:30

Das Ursprungsproblem ist gelöst :wink: Das war ne schwere Geburt!
Das ist sicher nicht die Eleganteste Lösung. Aber eine für Beginner verständliche :D

Folgender Algorithmus multipliziert die Elemente einer Eingegebenen Liste mit ihrem Index

Code: Alles auswählen

def MultiIndex(x):
    counter = 0
    listneu =[]
    while x != []:          # Bis die Eingegebene Liste leer ist:
     b = x[0]                # tue in b das ersten Element aus der Liste
     b = counter * b      # Multipliziert das Element mit seinem Index
     del x[0]                 # Lösche das Element aus der Liste
     listneu.append(b)    # Füge das Element zu einer neuen Liste hinzu
     counter = counter + 1
    return listneu

list = input("Gib eine Liste ein: ")    # Gib eine Liste ein
list =[int(i) for i in list.split(',')]      # Konvertiere in integer
list =  MultiIndex (list)                   
print (list)
BlackJack

@elNino: Was daran echt unschön ist, ist das verändern der an `MultiList()` übergebenen Liste. Ineffizient ist es zudem auch noch. Eine ``for``-Schleife über die Liste wäre auch viel einfacher (und wohl auch verständlicher). Und dann kann, wie ja schon gezeigt wurde, das manuelle verwalten von `counter` durch die `enumerate()`-Funktion ersetzt und damit vereinfacht werden.

Und „list comprehensions” kommen in den meisten Einsteigertutorials vor, sind ein wichtiger Bestandteil von Python, und Du verwendest sowieso schon eine. Also ist die ganze Funktion total lang und kompliziert.
Benutzeravatar
cofi
Python-Forum Veteran
Beiträge: 4432
Registriert: Sonntag 30. März 2008, 04:16
Wohnort: RGFybXN0YWR0

ViciousKitty hat geschrieben:Da kommt dann ein String. Aber überrascht mich jetzt nicht, wenn ich es mit einem String füttere?
Soso ein String? Nur, wenn man auch explizit einen String uebergibt:

Code: Alles auswählen

In [1]: a = input()
"1,2,3,4"

In [2]: b = input()
1,2,3,4

In [3]: type(a), a[0], type(a[0])
Out[3]: (str, '1', str)

In [4]: type(b), b[0], type(b[0])
Out[4]: (tuple, 1, int)
`input()` ist nichts anderes als `eval(raw_input())` und damit eine wunderbare Quelle an Sicherheitsluecken und ueberraschungen:

Code: Alles auswählen

In [5]: input()
Nice try!
  File "<string>", line 1
    Nice try!
           ^
SyntaxError: invalid syntax
Antworten