Autor |
Beitrag |
theevilworm
      
Beiträge: 61
|
Verfasst: Do 11.02.10 18:55
Hallo zusammen,
zuerst einmal: natürlich habe ich die Suche verwendet, es gibt da ein paar Threads zu Lottozahlen, aber meine Frage ist etwas anders.
Wir haben in der Schule in Informatik heute mit Arrays angefangen und sollten zum Anfang einen Lottozahlen-generator-Konzept entwickeln, mit einem Struktogramm.
Hier mal mein Versuch:
EDIT: Ups, erst nach dem Uploaden gemerkt: Die Abfrage, ob die Zahl schon mal gezogen wurde, wird ja nur einmal ausgeführt. Wenn die neue Zufallszahl unwahrscheinlicherweise nochmal die gleiche sein sollte, wird das ja nicht nochmal abgefragt. Deswegen muss die Abfrage in die Prozedur "Ziehen" rein.
Ich habe jedoch ein paar Probleme:
1. Ich habe das auf zwei Prozeduren bzw. Struktogramme aufgeteilt, da ich nicht wusste, wie ich sonst nochmal beliebig oft eine neue Zufallszahl generieren lassen sollte, falls die aktuelle in den letzten gezogenen Zahlen schon enthalten sein sollte
2. Ich habe die Zähschleife erst bei 2 starten lassen und davor manuell Lottozahlen[1] eine Zufallszahl zugewiesen, da ich ja sonst bei in der Zählschleife kein Lottozahl[i-1] gehabt hätte, mit dem ich hätte vergleichen können.
3. Aus den zwei Prozedure entsteht ein Problem: Die Zählervariable i muss global sein, damit die Prozedur "Ziehen" weiß, welchem Index von Lottozahl die Zufallszahl gewiesen werden muss. Mein Informatiklehrer meinte aber glaube ich mal, Zählervariablen lässt Delphi nicht global zu?
Falls es trotzdem in Delphi realisirbar sein sollte, ist es trotzdem ziemlich unelegant, oder? Wie könnte ich das besser machen? Ich danke euch für alle Antworten
Moderiert von Narses: Topic aus Delphi Language (Object-Pascal) / CLX verschoben am Fr 12.02.2010 um 17:33
Moderiert von Narses: Bild als Anhang hochgeladen.
Einloggen, um Attachments anzusehen!
|
|
Flamefire
      
Beiträge: 1207
Erhaltene Danke: 31
Win 10
Delphi 2009 Pro, C++ (Visual Studio)
|
Verfasst: Do 11.02.10 19:07
also
1) Die 2. Prozedur ist nicht nötig. Schreibs einfach rein. Wegen einer Anweisung brauch man keine 2.Prozedur, der du das Array und die Variable übergeben musst.
2) Statt dem Wenn, muss ein SOLANGE verwendet werden sonst:
Lottozahl[1]<-5
Für...
Lottozahl[2]<-5
Dann...
Lottozahl[2]<-5
Für...
Lottozahl[3]<-44
-->Die 5 kann (im Extremfall) mehrfach auftreten, da du nur nach der ersten zuweisung prüfst.
Dann lieber eine Fußgesteuerte Schleife, dann brauchst du auch die Anweisung nur einmal (zweimal mit dem einen vor der Für...)
|
|
theevilworm 
      
Beiträge: 61
|
Verfasst: Do 11.02.10 19:16
Hallo,
danke für deine Hilfe, hat mir nen Denkanstoß verpasst. Ist es so besser:
Moderiert von Narses: Bild als Anhang hochgeladen.
Einloggen, um Attachments anzusehen!
|
|
Flamefire
      
Beiträge: 1207
Erhaltene Danke: 31
Win 10
Delphi 2009 Pro, C++ (Visual Studio)
|
Verfasst: Do 11.02.10 19:22
besser ja
aber ich hatte was von fußgesteuerter schleife gesagt
guck dir die mal an 
|
|
theevilworm 
      
Beiträge: 61
|
Verfasst: Do 11.02.10 19:45
Hm, ich bin nicht sicher, was du meinst... Vielleicht so:
Aber wie sollte ich die Endbedingung in Delphi realisieren?
Delphi-Quelltext 1:
| Until Lottozahl[i] not in [Lottozahl[1]..Lottozahl[i-1]]; |
Ich glaube nicht, dass diese Zeile in Delphi durch den Debugger kommt.
Moderiert von Narses: Bild als Anhang hochgeladen.
Einloggen, um Attachments anzusehen!
|
|
Boldar
      
Beiträge: 1555
Erhaltene Danke: 70
Win7 Enterprise 64bit, Win XP SP2
Turbo Delphi
|
Verfasst: Do 11.02.10 20:01
Für zufällige, gleichverteilte Lottozahlen sollte man aber diesen Algorithmus benutzen:
www.delphi-library.d...t+shuffle_71713.html
|
|
Flamefire
      
Beiträge: 1207
Erhaltene Danke: 31
Win 10
Delphi 2009 Pro, C++ (Visual Studio)
|
Verfasst: Do 11.02.10 20:37
ist richtig!
auch delphi kann das.
3 schleifen arten
for: Zählschleife wenn anzahl vorher feststeht
kopfgesteuert, fußgesteuert: bedingung prüfen, fußgesteuert: wird mind. 1 mal ausgeführt
|
|
Marc.
      
Beiträge: 1876
Erhaltene Danke: 129
Win 8.1, Xubuntu 15.10
|
Verfasst: Fr 12.02.10 17:23
Da möchte ich noch einmal einen ganz interessanten Blog-Eintrag in die Runde werfen: The Danger of Naïveté. 
Für diesen Beitrag haben gedankt: Mitmischer 1703
|
|
theevilworm 
      
Beiträge: 61
|
Verfasst: Mo 15.02.10 13:43
Hi Leute, habe das gerade mal versucht in Delphi zu realisieren, doch folgendes klappt so nicht:
Delphi-Quelltext 1: 2: 3: 4: 5: 6: 7: 8: 9: 10: 11: 12: 13: 14: 15:
| procedure TForm1.Button1Click(Sender: TObject); var lottozahlen:array[0..6] of Integer; i:integer; begin lottozahlen[1]:=Random(49)+1;
For i:=2 to 6 do begin Repeat lottozahlen[i]:=Random(49)+1; Until lottozahlen[i] not in [Lottozahlen[1]..Lottozahlen[i-1]]; end;
end; |
Fehlermeldungen:
Zitat: |
Operator oder Semikolon fehlt
Operator ist auf diesen Operandentyp nicht anwendbar
|
EDIT:
Habs nun wenigstens zum Laufen gebracht, indem ich statt "Repeat...Until" "While" eingesetzt habe:
Delphi-Quelltext 1: 2: 3: 4: 5: 6: 7:
| For i:=2 to 6 do begin Randomize; Lottozahlen[i]:=Random(49)+1; While Lottozahlen[i] in [Lottozahlen[1]..Lottozahlen[i-1]] do Lottozahlen[i]:=Random(49)+1; end; |
Das startet ohne Fehlermeldungen, funktioniert aber nicht. Nach nur dreimal Generieren sind schon doppelte Zahlen erschienden, obwohl das doch eigentlich nicht passieren sollte!
|
|
martin300
      
Beiträge: 186
Erhaltene Danke: 2
|
Verfasst: Mo 15.02.10 15:13
Delphi-Quelltext 1: 2: 3: 4:
| Lottozahlen[i]:=Random(49)+1; While Lottozahlen[i] in [Lottozahlen[1]..Lottozahlen[i-1]] do Lottozahlen[i]:=Random(49)+1; <-- hier wird wieder eine neue Zahl erzeugt end; |
...es sollte jedoch die zuvor erzeugte verwendet werden und daher können sie doppelt sein.
|
|
martin300
      
Beiträge: 186
Erhaltene Danke: 2
|
Verfasst: Mo 15.02.10 15:18
Wenn ich mir Lottozahlen erzeugen müsste würde ich so vorgehen:
+ Menge der möglichen Zahlen (1..49) erzeugen
+ Zufallszahl generieren
+ Befindet sich Zahl in der Menge --> ja: Lottozahl speichern und aus möglichen Zahlen entfernen
--> nein: nochmal eine Zahl erzeugen
+ das ganze so oft wiederholen bis gewünschte Anzahl von Zahlen erzeugt wurde.
|
|
SvenAbeln
      
Beiträge: 334
Erhaltene Danke: 3
|
Verfasst: Mo 15.02.10 16:25
Zu deinem Fehler:
Zitat: |
Operator oder Semikolon fehlt
Operator ist auf diesen Operandentyp nicht anwendbar
|
In deiner Zeile muss das not an den Anfang:
Delphi-Quelltext 1:
| not (lottozahlen[i] in [Lottozahlen[1]..Lottozahlen[i-1]]) |
Dein Vergleich macht aber nicht das was du erwartest.
(lottozahlen[i] in [Lottozahlen[1]..Lottozahlen[i-1]]
Prüft nicht gegen alle Einträge deines Array, sondern nur ob die neue Zahl zwischen der ersten und der letzten Zahl ist.
z.B:
1 Zahl = 8
2 zahl = 25
Dann darf die dritte Zahl bei dir nicht zwischen 8 und 25 sein.
Für Lottozahlen[1] > Lottozahlen[i-1] ist dann jede Zahl erlaubt.
|
|
theevilworm 
      
Beiträge: 61
|
Verfasst: Mi 17.02.10 15:56
Hallo,
danke für eure Hinweise - da wäre ich gar nicht drauf gekommen. Doofe Logikfehler.
Und wie kann ich das jetzt so schreiben, dass es keine doppelten Zahlen generiert?
@martin300
Auch eine Möglichkeit, ich habe aber keine Ahnung, wie ich das realisieren könnten - hast du einen Tipp?
|
|
COMMANDER86
      
Beiträge: 167
Win XP, Win Vista
D3 Prof., D7 Pers., Lazarus
|
Verfasst: Do 18.02.10 00:14
Heyho,
ich habe sowas auch mal gebastelt:
Delphi-Quelltext 1: 2: 3: 4: 5: 6: 7: 8: 9: 10: 11: 12: 13: 14: 15: 16: 17: 18: 19:
| procedure TfrmLotto.btnGenerierenClick(Sender: TObject); var I, ZAHL: integer; label RETOUR; begin Randomize; ZAHL := Random(49) + 1;
for I := 1 to 6 do begin RETOUR: if ZahlenCheck(ZAHL) = True then begin ZAHL := Random(49) + 1; goto RETOUR; end else LOTTO[I] := ZAHL; end; |
Den Array (LOTTO) hab' ich da global deklariert, weil die Überprüfung, ob die Zahl im Array vorkommt (ZahlenCheck), ausgelagert ist:
Delphi-Quelltext 1: 2: 3: 4: 5: 6: 7: 8: 9: 10: 11: 12: 13: 14:
| function ZahlenCheck(ZAHL: integer): boolean; var I: integer; begin RESULT := False;
for I := 1 to 6 do begin if LOTTO[I] = ZAHL then begin RESULT := True; Exit; end; end; end; |
Der Rest ist noch eine Sortierung und die Ausgabe.
Ja, ich weiß... goto.  Ich bin der Meinung, dass man das an einer so übersichtlichen Stelle durchaus mal einsetzen darf.
LG
Fabian
_________________ Streichen Sie bitte sämtlichen Sarkasmus aus vorhergehender Nachricht. Dann wissen Sie, was ich sagen möchte. Meine Lösungen sind die vermutlich Umständlichsten, aber sie funktionieren (bei mir).
|
|
martin300
      
Beiträge: 186
Erhaltene Danke: 2
|
Verfasst: Do 18.02.10 11:21
hi,
hier eine andere Möglichkeit:
Delphi-Quelltext 1: 2: 3: 4: 5: 6: 7: 8: 9: 10: 11: 12: 13: 14: 15: 16: 17: 18: 19: 20: 21: 22: 23: 24: 25: 26: 27: 28: 29: 30:
| procedure TForm1.btn1Click(Sender: TObject); var lottozahlen : set of 1..49; lottozahl : array [1..6] of Integer; i: Integer; begin i := 1; while i <= 6 do begin lottozahl[i] := Random(49)+1; if (lottozahl[i] in lottozahlen) then begin i := i + 1; lottozahlen := lottozahlen - [lottozahl[i]]; end else begin end; end;
for i := 1 to 6 do begin mmo1.Lines.Add(IntToStr(lottozahl[i])); end; end; |
Für diesen Beitrag haben gedankt: Petroglyph
|
|
TechCruncher
Hält's aus hier
Beiträge: 2
|
Verfasst: Mi 12.10.11 18:44
Moderiert von Narses: Komplett-Zitat des letzten Beitrags entfernt.
Danke, der Code geht bei mir!!!
Ich würde das gerne für ein weiteres Tool für [url= www.gewinn-zahlen.co...us49-lotto-samstag/]lottozahlen[/URL] nutzen, darf man das überhaupt oder muss man zuerst um Zustimmung bitten?
|
|