pbm-Flagge

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.
Meishere
User
Beiträge: 27
Registriert: Montag 24. Januar 2011, 16:54

Hallo,
Jetzt wende ich mich auch mal mit einem Problem bei meine Schulaufgaben an euch. Natürlich öchte ich nicht, dass ihr mir meine Hausaufgaben macht, aber ich komme einfach nicht weiter und dachte eigentlich ich hätte das alles verstanden :(

Also, meine Aufgabe ist es ein paar Flagge (nach Vorgabe) zu erstellen.
Alle Flaggen sollen 300x200 pixel groß sein und in Python als .py Datei abgespeichert und dann per cmd von Windows in .pbm-Dateien umgewandelt werden.
Ich habe es auch ziemlich schnell geschafft eine Flagge zu erstellen und zwar "obere Hälfte schwarz, untere Hälfte weiß".
Und auch von oben nach unten 3 Streifen und eine dritte mit 8 Streifen waren relativ einfach.

Allerdings bin ich an meine Grenzen gestoßen, als es darum ging eine Flagge zu machen, deren linke Hälfte schwarz und deren rechte Hälfte weiß ist.

Mein Code sieht so aus:

Code: Alles auswählen

#Flagge:  Flagge5
#Version: 2.5.4

def schleife(a):
    for spalte in range(1,201):    #Komplett die Spalte ausfüllen
        for zeile in range(1,151):  #Bis zur Hälfte die Zeile auffüllen
            print a,
        print

print("P1")
print("300,200")
print schleife(1)
print schleife(0)
Wie in den Kommentaren geschrieben, dachte ich, dass das Programm zuerst die Linke Hälfte mit Schwarz und dann die rechte Hälfte mit weiß füllt. Allerdings wird die obere Hälfte mit Schwarz und die untere Hälfte mit weiß gefüllt.
Und ich verstehe einfach nicht warum. Diese Programm macht dann ja genau das gleiche wie dieses:

Code: Alles auswählen

#Flagge:  Flagge1
#Version: 2.5.4

def schleife(a):
    for spalte in range(1,101):
        for zeile in range(1,301):
            print a,
        print

print("P1")
print("300,200")
print schleife(1)
print schleife(0)
Ich bin ein wenig verwirrt und hoffe auf baldige Hilfe :D
Danke im vorraus
Jetzt sind die guten alten Zeiten, nach denen wir uns in zehn Jahren zurücksehnen.
Peter Ustinov

Jeder Mensch macht Fehler. Das Kunststück liegt darin, sie dann zu machen, wenn keiner zuschaut.
Peter Ustinov
Benutzeravatar
/me
User
Beiträge: 3561
Registriert: Donnerstag 25. Juni 2009, 14:40
Wohnort: Bonn

Meishere hat geschrieben:Und ich verstehe einfach nicht warum. Diese Programm macht dann ja genau das gleiche wie dieses:
Da fehlen wohl elementare Grundkenntnisse die man euch nicht beigebracht hat. Der zweite Code sieht doch genau aus wie der erste, von der Anzahl der Schleifendurchläufe mal abgesehen. Ich kenne das gewünschte Format zwar nicht, aber aus dem Code lässt sich relativ leicht schließen wie das aussehen müsste.

Mal als Ansatz:

Code: Alles auswählen

for _ in range(200):
    for y in range(300):
        if y <= 150:
            [...]
Noch Fragen?
Meishere
User
Beiträge: 27
Registriert: Montag 24. Januar 2011, 16:54

Nunja, erstmal danke für deine Hilfe. So wie du es sagst würde es natürlich gehen, aber ich fürchte, dass meine Lehrerin von uns verlangt, es so zu machen, wie wir es gelernt haben :D

Aber ich kann es natürlich so versuchen und sie einfach mal fragen, ob es so OK ist ;)

EDIT: Hmm. Verdammt. Das geht doch nicht. Es passiert genau das gleiche, wie bei meinem Code. Außerdem ist es offenbar besser for x in range(1,201) zu verwenden, da sonst bei dem fertigen Bild ein "Treppchen-Effekt" entsteht.

Ich hoffe, dass wir die Lösung noch finden :D
Zuletzt geändert von Meishere am Samstag 19. März 2011, 13:58, insgesamt 1-mal geändert.
Jetzt sind die guten alten Zeiten, nach denen wir uns in zehn Jahren zurücksehnen.
Peter Ustinov

Jeder Mensch macht Fehler. Das Kunststück liegt darin, sie dann zu machen, wenn keiner zuschaut.
Peter Ustinov
BlackJack

@Meishere: Dein Quelltext schreibt erst ein Anzahl 1er-Zeilen und dann eine Anzahl 0er-Zeilen. Was Du haben möchtest ist aber eine Anzahl Zeilen in denen *beides* vorkommt. Das kann man nicht erreichen in dem man einfach nur die Anzahl und Länge der Zeilen aus dem ersten Beispiel ändert. Eure Lehrerin will sicher das ihr nachdenkt und lernt wie man Schleifen verwendet. In welcher Reihenfolge was ausgeführt wird.

Die Ausgaben mit ``print`` erfolgen immer hintereinander weg als ein Datenstrom. Es ist nicht möglich da zurück zu gehen und an die Zeilen noch etwas anzuhängen. Wenn Du das also so beibehalten willst, dann musst Du die 0en, 1en und Zeilenumbrüche schon in der richtigen Reihenfolge erzeugen.

Schreib Dir doch mal mit einem Texteditor eine kleine PBM-Datei mit einer 4×2 Flagge mit dem entsprechenden Muster und dann überlege Dir Schritt für Schritt wie Du die per Programm erstellen würdest. Zeile für Zeile, Pixel für Pixel.
Meishere
User
Beiträge: 27
Registriert: Montag 24. Januar 2011, 16:54

Ja natürlich...
Danke BlackJack :)
Ich glaube eher, dass ich mal wieder auf dem Schlauch stehe/stand. Das Thema mit den Schleifen haben wir im Grunde schon abgehakt. Aber ich war so fixiert auf die Idee, die ich hatte, dass ich das Problem nicht erkannt habe.
Ich werde mich gleich mal dransetzen und es überarbeiten.
Jetzt sind die guten alten Zeiten, nach denen wir uns in zehn Jahren zurücksehnen.
Peter Ustinov

Jeder Mensch macht Fehler. Das Kunststück liegt darin, sie dann zu machen, wenn keiner zuschaut.
Peter Ustinov
Benutzeravatar
/me
User
Beiträge: 3561
Registriert: Donnerstag 25. Juni 2009, 14:40
Wohnort: Bonn

Meishere hat geschrieben:Nunja, erstmal danke für deine Hilfe. So wie du es sagst würde es natürlich gehen, aber ich fürchte, dass meine Lehrerin von uns verlangt, es so zu machen, wie wir es gelernt haben :D
Man muss sich schon seine eigenen Gedanken machen, wie man Dinge umsetzt und ich denke, dass genau das von euch erwartet wird. Softwareentwicklung ist mehr als Copy & Paste. Ein zweimaliger Aufruf der äußeren Schleife ist doch völlig offensichtlich verkehrt, da sich innerhalb einer Spalte die Farbe niemals ändert. Was du brauchst ist eine Änderung der Werte in der Zeile und das geht nur in der inneren Schleife. Ich habe jetzt if als Möglichkeit angegeben, du kannst aber natürlich auch einfach zwei (innere) Schleifen hintereinander setzen und in jeder von ihnen den jeweils passenden Wert ausgeben.

Solltet ihr übrigens tatsächlich gelernt haben, dass man range(1, 11) statt range(10) verwendet, dann benötigt eure Lehrerin definitiv etwas mehr pythonisches Denken.
BlackJack

@Meishere: Neben den Argumenten für `range()` die /me schon erwähnte solltest Du bei Python 2.x auch `xrange()` verwenden und die Klammern um die "Argumente" von ``print`` weg lassen. Das ist nämlich keine Funktion und Klammern können an der Stelle unter Umständen auch zu falschen Ergebnissen führen.

Ausserdem gehört das Komma bei ``print '300,200'`` nicht zwischen die 300 und die 200. Die meisten Grafikprogramme werden so ein Bild wahrscheinlich trotzdem lesen können, aber laut Spezifikation gehört das da nicht hin.

Solltet ihr irgendwann eine Japanische Flagge erstellen sollen, dann gibt es dafür auch schon eine umfangreiche Diskussion: http://www.python-forum.de/viewtopic.php?f=1&t=13537 :-)
Meishere
User
Beiträge: 27
Registriert: Montag 24. Januar 2011, 16:54

Nunja. Ich weiß auch nicht wieso sie uns das mit in range so beigebracht hat. Sie ist sogar noch Referendarin und sollte eigentlich "näher am Geist der Zeit" liegen als ältere Lehrer.

Entschuldigung, dass ich das nicht selbst erkannt habe :oops: Wie gesagt, jetzt finde ich es auch ziemlich offensichtlich. :?

Naja, Danke nochmal an euch beide :D

EDIT: Ich habe jetzt erst den Beitrag von BlackJack gesehen ;) Also... Ich kann halt nur so arbeiten, wie es mir erklärt wird und meine Lehrerin hat uns halt gesagt, dass da ein Komma hinsoll. Und ich kenne auch noch nicht alle "Syntax-Begriffe".
Daher werde ich den Code lieber so lassen, wie unsere Lehrerin ihn haben will und mir privat merken, wie es besser geht. So läuft das halt manchmal in der Schule :D
Jetzt sind die guten alten Zeiten, nach denen wir uns in zehn Jahren zurücksehnen.
Peter Ustinov

Jeder Mensch macht Fehler. Das Kunststück liegt darin, sie dann zu machen, wenn keiner zuschaut.
Peter Ustinov
Meishere
User
Beiträge: 27
Registriert: Montag 24. Januar 2011, 16:54

Eine Frage hätte ich doch noch.
Das Problem ist auch in der Schule aufgetreten und unsere Lehrerin hatte auch keine Ahnung, warum das passiert :roll:

Undzwar geht es immernoch um die Fahnen.
Wenn man den Code als Funktion schreibt, um den Quelltext kürzer zu machen, dann entsteht ein Treppchen-Effekt im fertigen Bild.
Weiß jemand woran das liegen könnte?
Jetzt sind die guten alten Zeiten, nach denen wir uns in zehn Jahren zurücksehnen.
Peter Ustinov

Jeder Mensch macht Fehler. Das Kunststück liegt darin, sie dann zu machen, wenn keiner zuschaut.
Peter Ustinov
Benutzeravatar
numerix
User
Beiträge: 2696
Registriert: Montag 11. Juni 2007, 15:09

BlackJack hat geschrieben:Solltet ihr irgendwann eine Japanische Flagge erstellen sollen, dann gibt es dafür auch schon eine umfangreiche Diskussion: http://www.python-forum.de/viewtopic.php?f=1&t=13537 :-)
Ach ja, war das ein Spaß damals ... :lol:
EyDu
User
Beiträge: 4881
Registriert: Donnerstag 20. Juli 2006, 23:06
Wohnort: Berlin

Hallo.

Zeige mal den Code, welcher den Fehler produziert. Mit raten kommt man bei solchen Problemen nicht weiter.
numerix hat geschrieben:
BlackJack hat geschrieben:Solltet ihr irgendwann eine Japanische Flagge erstellen sollen, dann gibt es dafür auch schon eine umfangreiche Diskussion: http://www.python-forum.de/viewtopic.php?f=1&t=13537 :-)
Ach ja, war das ein Spaß damals ... :lol:
Dass das schon wieder drei Jahre her ist ... :-)
Das Leben ist wie ein Tennisball.
Meishere
User
Beiträge: 27
Registriert: Montag 24. Januar 2011, 16:54

Oh entschuldigung, ich dachte ich hätte den Code schon gepostet.

Code: Alles auswählen

#Flagge:  Flagge5
#Version: 2.5.4

def schleife(a,b):
    for spalte in range(1,151):
        for zeile in range(1,26):
            print a,
        print
        for zeile2 in range(1,26):
            print b,
        print

print("P1")
print("300,200")

for x in range(1,5):
    print schleife(1,0)
    print schleife(0,1)
Da ist er :D
Jetzt sind die guten alten Zeiten, nach denen wir uns in zehn Jahren zurücksehnen.
Peter Ustinov

Jeder Mensch macht Fehler. Das Kunststück liegt darin, sie dann zu machen, wenn keiner zuschaut.
Peter Ustinov
EyDu
User
Beiträge: 4881
Registriert: Donnerstag 20. Juli 2006, 23:06
Wohnort: Berlin

Ich tippe mal darauf, dass du nicht die Ergebnisse von "schleife" ausgeben möchtest.
Das Leben ist wie ein Tennisball.
Meishere
User
Beiträge: 27
Registriert: Montag 24. Januar 2011, 16:54

Wie meinst du das?
Ich denke eigentlich schon, dass die Ergebnisse ausgegeben werden müssen. Die Funktion "erstellt" doch sotusagen die Flagge und der print-Befehlt gibt diese dann aus, oder?
Jetzt sind die guten alten Zeiten, nach denen wir uns in zehn Jahren zurücksehnen.
Peter Ustinov

Jeder Mensch macht Fehler. Das Kunststück liegt darin, sie dann zu machen, wenn keiner zuschaut.
Peter Ustinov
EyDu
User
Beiträge: 4881
Registriert: Donnerstag 20. Juli 2006, 23:06
Wohnort: Berlin

Meishere hat geschrieben:Wie meinst du das?
Ich denke eigentlich schon, dass die Ergebnisse ausgegeben werden müssen. Die Funktion "erstellt" doch sotusagen die Flagge und der print-Befehlt gibt diese dann aus, oder?
Nein, die Ausgabe wird bereits in der "schleife"-Funktion gemacht, diese gibt nichts (außer None) zurück. Genau diese "None"s gibtst du dann allerdings aus. Das siehst du auch, wenn du dir die Ausgabe anschaust.
Das Leben ist wie ein Tennisball.
BlackJack

@Meishere: Also einfach Fehler unkommentiert übernehmen ist etwas was man in der Schule nicht machen sollte. Schule soll einen doch nicht zu einem tumben Befehlsempfänger erziehen, der nichts in Frage stellt. Wenn das Daten im Portable Bitmap (PBM) Format sein sollen, dann ist das Komma an der Stelle falsch. Ein Lehrer der eine Korrektur mit Begründung an der Stelle nicht anerkennt, sollte vielleicht einen anderen Beruf wählen. Wichtig ist die Begründung, so dass der Lehrer nicht denkt es war eine Unachtsamkeit von Dir das Komma weg zu lassen. Man könnte also zum Beispiel die Stelle kommentieren, dass da vorher ein Komma stand, an der Stelle laut Spezifikation aber nur "whitespace" erlaubt ist. Als Quelle kann man zum Beispiel Wikipedia (http://de.wikipedia.org/wiki/Portable_Bitmap) oder die Dokumentation von netpbm (http://netpbm.sourceforge.net/doc/pbm.html) angeben.

Die ganzen Zahlen da hart rein zu schreiben ist nicht besonders wartbar. An den `range()`-Argumenten ist auch unschön, dass man nachdenken muss wenn man beide Argumente übergibt. Bei einem ``range(25)`` sieht man viel leichter wie viele Elemente da in der Liste enthalten sind -- kann man einfach ablesen: 25. Bei ``range(1, 26)`` muss man sich beide Argumente anschauen und dann auch noch rechnen um auf die 25 zu kommen.
Meishere
User
Beiträge: 27
Registriert: Montag 24. Januar 2011, 16:54

@BlackJack: Ja du hast natürlich recht und unsere Lehrerin ist auch nicht so, dass sie wütend wäre oder sich nicht "verbessern" lässt.
Ich werde sie aber erst in der nächsten Informatik-Stunde drauf ansprechen und habe erstmla meine Hausaufgaben so gemacht "wie sie es will". Solange es funktioniert ist es ja nur ein "Schönheitsfehler".

@EyDu: Ah. Jetzt habe ich dich verstanden. Einfach schleife ohne print aufrufen und schon klappt's. Da hat mir wieder meine Lehrerin was falsches erzählt bzw. uns etwas vorenthalten... Nämlich, dass man Funktionen auch ohne "print" ausgeben kann-.-

EDIT: Ok, ich habe jetzt doch meine Lehrerin informiert und das Ganze auch in den Kommentaren geschrieben. Mal sehen wie sie reagiert.
Jetzt sind die guten alten Zeiten, nach denen wir uns in zehn Jahren zurücksehnen.
Peter Ustinov

Jeder Mensch macht Fehler. Das Kunststück liegt darin, sie dann zu machen, wenn keiner zuschaut.
Peter Ustinov
EyDu
User
Beiträge: 4881
Registriert: Donnerstag 20. Juli 2006, 23:06
Wohnort: Berlin

Meishere hat geschrieben:@EyDu: Ah. Jetzt habe ich dich verstanden. Einfach schleife ohne print aufrufen und schon klappt's. Da hat mir wieder meine Lehrerin was falsches erzählt bzw. uns etwas vorenthalten... Nämlich, dass man Funktionen auch ohne "print" ausgeben kann-.-
Ich würde sagen, dass du da eher etwas falsch verstanden hast ;-) "print" macht die Ausgabe von Werten und hat keine magischen Auswirkungen auf die möglicherweise aufgerufenen Funktionen. Funktionen führen lediglich die in ihnen enthaltenen Anweisungen aus. Und wenn da ein "print" steht, dann wird eben einfach etwas ausgegeben. Ist es eine Addition, dann wird eben etwas addiert.

Sebastian
Das Leben ist wie ein Tennisball.
Meishere
User
Beiträge: 27
Registriert: Montag 24. Januar 2011, 16:54

Hmmm... Ok.
Dann habe ich dich wohl doch flasch verstanden...
Aber dann frage ich mich, wieso der Fehler nicht mehr auftritt, wenn man print wegnimmt.
Jetzt sind die guten alten Zeiten, nach denen wir uns in zehn Jahren zurücksehnen.
Peter Ustinov

Jeder Mensch macht Fehler. Das Kunststück liegt darin, sie dann zu machen, wenn keiner zuschaut.
Peter Ustinov
Benutzeravatar
cofi
Python-Forum Veteran
Beiträge: 4432
Registriert: Sonntag 30. März 2008, 04:16
Wohnort: RGFybXN0YWR0

Um EyDu zu ergaenzen: Funktionen fuehren nur den Code aus den sie enthalten, aber geben _immer_ auch etwas zurueck. Gibt es kein explizites `return` in der Funktion wird `None` zurueckgegeben.
Und damit ist das `print` an der Stelle (fast) dasselbe wie folgendes:

Code: Alles auswählen

In [1]: print None
None
Antworten