2010-05-31 4 views
11

Also, in Python (obwohl ich glaube, es kann in viele Sprachen angewendet werden), finde ich mich mit so etwas wie dies oft:kleine Code-Redundanz innerhalb while-Schleifen (nicht sauber fühlen)

the_input = raw_input("what to print?\n") 
while the_input != "quit": 
    print the_input 
    the_input = raw_input("what to print?\n") 

Vielleicht bin ich zu wählerisch, aber ich mag es nicht, wie die Zeile the_input = raw_input("what to print?\n") wiederholt werden muss. Es verringert Wartbarkeit und Organisation. Aber ich sehe keine Problemumgehungen, um den doppelten Code zu vermeiden, ohne das Problem weiter zu verschlimmern.

while ((the_input=raw_input("what to print?\n")) != "quit") { 
    print the_input 
} 

Dies ist definitiv nicht Pythonic und Python nicht einmal erlauben, für die Zuweisung innerhalb der Schleife Bedingungen AFAIK: In einigen Sprachen, konnte ich so etwas schreiben.

Dieser gültiger Code behebt die Redundanz,

while 1: 
    the_input = raw_input("what to print?\n") 
    if the_input == "quit": 
     break 
    print the_input 

Aber fühlen entweder nicht ganz. Die while 1 impliziert, dass diese Schleife für immer ausgeführt wird; Ich benutze eine Schleife, aber gebe ihr einen falschen Zustand und lege den echten hinein.

Bin ich zu wählerisch? Gibt es einen besseren Weg, dies zu tun? Vielleicht gibt es dafür ein Sprachkonstrukt, von dem ich nichts weiß?

+1

Ich denke, die erste Form ist absolut akzeptabel. –

+5

Dies ist ein gängiges Muster namens [Schleife und eine Hälfte] (http://www.cs.duke.edu/~ola/patterns/plopd/loops.html#loop-and-a-half). –

Antwort

30

Denken Iteratoren - zum Beispiel in diesem speziellen Fall:

for the_input in iter(lambda: raw_input('what to print?\n'), 'quit'): 
    print the_input 

meisten Schleifen in Python, mit Ausnahme der untersten Abstraktionsebenen, wird am besten als for Schleifen mit der Hilfe einiger Untergebener umgesetzt Iterator, der die "looping Logik" erfasst - die iter Built-in kann helfen (wie hier), manchmal Genexps (Generator Ausdrücke) kann, manchmal die Standard-Bibliothek Modul itertools kommt zur Rettung.

Am häufigsten werden Sie wählen benutzerdefinierte Generator Funktionen (diejenigen mit yield) oder mehr gelegentlich kodieren (wenn Sie wirklich anspruchsvolle Statusverwaltung benötigen) eine benutzerdefinierte Iterator-Klasse (eine der __iter__ spezielle Methode als return self definiert, und next [[oder __next__ in den neuesten Versionen von Python]] zurückzukehren „, um den nächsten Wert aus der Iteration).

Capturing the looping Logik abgesehen von was auch immer es ist, dass Sie auf den verschiedenen Elementen tun sequentiell erzeugt durch die Schleife itse Hier ist der Schlüssel zur Abstraktion!

+4

Das fühlt sich einfach ein wenig zu schlau an ... –

+0

+1: Lieber 'for'-Schleifen für die Iteration bevorzugen. In jeder Sprache, die sie bietet. – Johnsyweb

+0

Dies ist eine erstaunliche Lösung. SO wird mich eine Antwort für weitere 4 Minuten nicht akzeptieren lassen ;-) – Ponkadoodle