Autor Beitrag
steve110
Hält's aus hier
Beiträge: 14



BeitragVerfasst: So 28.12.08 15:06 
Hallo zusammen, hoffentlich hattet ihr alle schöne Weihnachten!!

Wir sollen bis nach den Ferien anfangen das Spiel 17 und 4 zu programmieren... Unserer konkrete Aufgabe besteht darin, dass das Programm ersteinmal die Karten mischen soll, mehr soll es zunächst nicht können...

Wir haben aber vor den Ferien nichts, aber auch wirklich gar nichts über dynamische Listenstrukturen, o. ä. gemacht. Das Programm soll allerdings damit aufgebaut sein ;-((( :cry: :cry: :cry: Außerdem weiß ich nicht wie man die Karten überhaupt mischt wenn man auf einen Button klickt...

Ich wollte euch fragen, ob jemand von euch mir ein Programm schreiben kann, der es ermöglicht die 32 Karten zu mischen wenn man auf einen Button klickt??? Das wäre wirklich super nett, ich hab wirklich nicht die geringste Ahnung wie ich anfangen soll :cry: :cry:

Danke schonmal
LG


Moderiert von user profile iconNarses: Topic aus VCL (Visual Component Library) verschoben am So 28.12.2008 um 14:56
Calculon
ontopic starontopic starontopic starontopic starontopic starontopic starofftopic starofftopic star
Beiträge: 676

Win XP Professional
Delphi 7 PE, Delphi 3 PRO
BeitragVerfasst: So 28.12.08 15:28 
Ich würde vorschlagen du erzeugst erstmal ein statisches array of string in das du die Kartenbezeichner packst:

ausblenden Delphi-Quelltext
1:
2:
3:
4:
5:
var
  cards: array [0..31of string;
begin
  cards[0] := 'Herz Ass';
  cards[1] := {etc.}

Dann kannst du mit Hilfe von randomize und random eine Stringliste zufällig füllen.

Et voilà

Edit: Wobei mir gerade einfällt, dass diese Vorgehensweise nicht so optimal ist, da du sicherstellen musst, dass der Zufallswert nicht doppelt in der Stringliste auftaucht. Deshalb statt einem statischen array of string doch lieber gleich eine weitere (oder auch dieselbe) Stringliste verwenden.

Gruß
--

_________________
Hallo Mutti
steve110 Threadstarter
Hält's aus hier
Beiträge: 14



BeitragVerfasst: Di 30.12.08 09:36 
hallo, danke ersteinmal für deine Antwort!!! Muss ich in den Array dann alle 31 Karten (eigtl 32??) Karten eintragen?

Der von dir geschriebene Code muss doch dann in die Button Procedure, oder?
Wo bekomme ich denn die Spielkarten als Grafiken her, damit man die auch verwenden und vorallem mischen kann???

Danke schonmal,
LG
baka0815
ontopic starontopic starontopic starontopic starontopic starontopic starontopic starofftopic star
Beiträge: 489
Erhaltene Danke: 14

Win 10, Win 8, Debian GNU/Linux
Delphi 10.1 Berlin, Java, C#
BeitragVerfasst: Di 30.12.08 10:46 
user profile iconsteve110 hat folgendes geschrieben Zum zitierten Posting springen:
hallo, danke ersteinmal für deine Antwort!!! Muss ich in den Array dann alle 31 Karten (eigtl 32??) Karten eintragen?

Es sind schon 32 Elemente im Array und zwar 0..31, also die Elemente 0 bis 31 (inklusive), macht 32 Stück.

Zitat:
Der von dir geschriebene Code muss doch dann in die Button Procedure, oder?

Ich denke, du möchtest die Karten bzw. den Kartenstapel bestimmt später noch nutzen, zum Geben der Karten z.B.
Daher wäre es nicht sinnvoll die Variable in die Knopf-Klick-Prozedur zu setzen, da dann der Inhalt nicht mehr definiert wäre, sobald die Prozedur zu Ende ist. Du hättest also keine Möglichkeit mehr, nach dem Mischen auf deine Karten zuzugreifen.
Daher solltest du die Variable global definieren, da du ja zu jedem Zeitpunkt aus deinem Spiel heraus auf den Kartenstapel zugreifen musst.

Was allerdings den Vorschlag angeht, das als Liste von Strings zu handhaben, finde ich das ganze nicht optimal. Es geht ja bei 17+4 auch um die Wertigkeiten der Karten und wenn du die Karten "Herz Ass", "Herz 7", "Pik 3", etc. nennst, dann musst du den String jedes Mal in "Herz" und "Ass" zerpflücken und dann die Wertigkeit ermitteln.

Schau dir mal diese Diskussion an, vielleicht hilft dir das was und mit Records habt ihr doch bestimmt schon gearbeitet?

Zitat:
Wo bekomme ich denn die Spielkarten als Grafiken her, damit man die auch verwenden und vorallem mischen kann???

Die Grafiken müsstest du dann jeder Karte gesondert zuordnet. Ich würd einfach mal im Internet suchen ob du die Karten irgendwo findest.
Im Debian Pojekt gibt es zum Beispiel das Paket gnome-cards-data, das man mit 7-zip auspacken können müsste. Darin sind zwei Kartensets: /usr/share/gnome-games-common/cards/bonded.svg und /usr/share/gnome-games-common/cards/gnomangelo_bitmap.svg. Zwar beide als SVG, aber mit GIMP o.ä. kann man die konvertieren.
Fiete
ontopic starontopic starontopic starontopic starontopic starontopic starontopic starontopic star
Beiträge: 617
Erhaltene Danke: 364

W7
Delphi 6 pro
BeitragVerfasst: Di 30.12.08 11:02 
Moin steve110,
du solltest erst mal Datentypen erfinden wie
ausblenden Delphi-Quelltext
1:
2:
3:
4:
5:
6:
7:
8:
9:
10:
11:
12:
const KartenAnzahl=52;Kartenspiele=2;MaxKarten=KartenAnzahl*Kartenspiele;
      
type
      TKartenFarbe=(Kreuz,Pik,Herz,Karo);
      TKartenWert=(Zwei,Drei,Vier,Fuenf,Sechs,Sieben,Acht,
                   Neun,Zehn,Bube,Dame,Koenig,Ass);
      TKarte=Record
              Farbe:TKartenFarbe;
              Bezeichnung:TKartenWert;
              KartenWert:Integer
             end;
      TSpiel=Array[1..MaxKarten] of TKarte;

Dann hab ich zwei Prozeduren erstellt
ausblenden volle Höhe 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:
31:
32:
33:
34:
35:
36:
37:
procedure KartenspielGenerieren(var SP:TSpiel);
procedure Mischen(var SP:TSpiel);

procedure TBJ.KartenspielGenerieren(var SP:TSpiel);
  var F:TKartenFarbe;
      W:TKartenWert;
      K:Integer;
  begin
   for K:=0 to Kartenspiele-1 do
    for F:=Kreuz to Karo do
     for W:=Zwei to Ass do
      with SP[K*KartenAnzahl+(ord(F)*13+ord(W)+1)] do
       begin
        Farbe:=F;Bezeichnung:=W;
        case W of
          Zwei..Zehn : KartenWert:=2+ord(W);
          Ass : KartenWert:=11
          else KartenWert:=10
        end
       end
  end;

 procedure TBJ.Mischen(var SP:TSpiel);
  var Benutzt:Array[1..MaxKarten] of Boolean;
      I,T:Integer;
      Neu:TSpiel;
  begin
   KartenspielGenerieren(Neu);
   FillChar(Benutzt,SizeOf(Benutzt),0);
   for I:=1 to MaxKarten do
    begin
     repeat
      T:=1+random(MaxKarten);
     until not Benutzt[T];
     SP[I]:=Neu[T];Benutzt[T]:=True
    end
  end;


Die Bilder kannst Du in einem TImage anzeigen lassen.
Die Bilder selbst hab Solitär geklaut, cards.dll in c:\windows\system32

Viel Erfolg
Fiete

_________________
Fietes Gesetz: use your brain (THINK)
steve110 Threadstarter
Hält's aus hier
Beiträge: 14



BeitragVerfasst: Di 30.12.08 14:38 
Hallo zusammen, danke für eure Antworten, ich wollte gerade anfangen eure Vrschläge weiter auszubauen und zu nutzen, da sehe ich in einer E-Mail von unserem Lehrer dass wir ein bereits erstelltes Programm weiter bearbeiten sollen und die Mischfunktion da hineinarbeiten sollen... :shock:

Es sind drei .pas Dateien und halt das Formular, ich hab alles mal in den Anhang gepackt...ich weiß jetzt überhaupt nicht mehr wo ich anfangen soll und wo was hinein soll...übrigens habe ich jetzt auch die Grafikdateien, sind auch im Anhang...

Hoffentlich blickt ihr da durch :cry: :cry:

Irgendwo da muss eine Mischfunktion implementiert werden... :?: :?:
Einloggen, um Attachments anzusehen!
baka0815
ontopic starontopic starontopic starontopic starontopic starontopic starontopic starofftopic star
Beiträge: 489
Erhaltene Danke: 14

Win 10, Win 8, Debian GNU/Linux
Delphi 10.1 Berlin, Java, C#
BeitragVerfasst: Di 30.12.08 14:56 
Ohne mir den Quellcode jetzt anzugucken, kannst du dir mal diesen Beitrag von Narses mal anschauen, da ist eine Möglichkeit des Mischens beschrieben.
jaenicke
ontopic starontopic starontopic starontopic starontopic starontopic starontopic starofftopic star
Beiträge: 19312
Erhaltene Danke: 1747

W11 x64 (Chrome, Edge)
Delphi 11 Pro, Oxygene, C# (VS 2022), JS/HTML, Java (NB), PHP, Lazarus
BeitragVerfasst: Di 30.12.08 15:06 
:shock: Seltsame Quelltext"formatierung", und dazu noch GIFs, die Delphi 6/7 direkt erstmal gar nicht lesen kann...
Naja, ich rede besser nicht weiter... :roll:

Jedenfalls sind die von Fiete genannten Datentypen bereits in mCardType.pas angedeutet:
ausblenden Delphi-Quelltext
1:
2:
3:
4:
5:
6:
7:
8:
9:
10:
11:
12:
13:
type
TCard = class
         private

         public

end;
TCardDeck = class(TStack)
          private

          public

end;
Zusätzlich ist eine fertige Stackimplementierung in mStack.pas vorhanden. Ihr werdet also vermutlich bereits etwas mit Stacks gemacht haben? Ist dir klar was das ist?
steve110 Threadstarter
Hält's aus hier
Beiträge: 14



BeitragVerfasst: Fr 02.01.09 10:42 
Hallo, sorry dass ich jetzt erst antworte, war über Silvester weg. Wünsche euch trotzdem ein frohes neues Jahr 2009!!!

Wir haben ganz kurz über Stacks gesprochen, in unserem Fall (dem Kartenspiel) steht Stack doch für den Kartenstapel, oder??? Der Quelltext ist auch total daneben, ich hab auch wirklich keine Ahnung wie ich das machen soll... :(

Wie wird dann die Mischfunktion implementiert??
steve110 Threadstarter
Hält's aus hier
Beiträge: 14



BeitragVerfasst: Mo 05.01.09 09:32 
Hallo zusammen,
ich hab jetzt erstmal verschiedene Klassen für das Spiel erstellt (TForm, TCard, TStack,.....) Der nächste Schritt sollte jetzt sein, die Klassen in die Delphi Vorlage zu implementieren, die ich bereits ein paar Posts vorher hochgeladen habe!!

Meine Bitte an euch, kann jemand eine oder zwei Klassen implementieren, damit ich sehe wohin Sie gehört und wie das aufgeschrieben werden muss?? Bitte implementiert mir die Klassen, die ich als Datei angehangen habe in das Delphiprojekt von oben!!!

Ganz großes Dankeschön schonmal :oops:
Einloggen, um Attachments anzusehen!
steve110 Threadstarter
Hält's aus hier
Beiträge: 14



BeitragVerfasst: Mo 05.01.09 20:41 
kann mir keine helfen?? Bitte helft mir und zeigt mir wo und wie ich die Klassen implemetieren muss!! :cry: :cry:

Bitte!!! :(

Danke schonmal!!!!
jaenicke
ontopic starontopic starontopic starontopic starontopic starontopic starontopic starofftopic star
Beiträge: 19312
Erhaltene Danke: 1747

W11 x64 (Chrome, Edge)
Delphi 11 Pro, Oxygene, C# (VS 2022), JS/HTML, Java (NB), PHP, Lazarus
BeitragVerfasst: Mo 05.01.09 20:58 
Erstens sind Schiebepostings, also Antworten nur zur Erinnerung an die Frage, hier erst nach 24 Stunden erlaubt. Und das waren jetzt gerade einmal 11.

Zweitens habe ich von dir bisher keinen Quelltext hier gesehen (außer der Vorgabe, aber ich meine selbst geschriebenen). Versuche es doch einfach erstmal und zeige dann wie weit du gekommen bist.
lincore
Hält's aus hier
Beiträge: 15

Kubuntu 8.04, Debian lenny, Windows XP, Windows Vista
Delphi 2009, C++, Python, Lua
BeitragVerfasst: Mo 05.01.09 22:27 
Ich finde es schon ein wenig grenzwertig, sich die Arbeit abnehmen zu lassen ohne dabei einen Funken Eigeninitiative durchblicken zu lassen. Da reicht ein Dankeschön meines Erachtens nicht. Harte Währung erscheint mir eher angemessen... schicke mir zwecks Bankverbindung einfach eine Nachricht. Als kleines Appetithäppchen (und weil ich nichts Besseres zu tun habe) gibts den folgenden Code ausnahmsweise gratis:

ausblenden volle Höhe 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:
31:
32:
33:
34:
35:
36:
37:
38:
39:
40:
41:
42:
43:
44:
45:
46:
47:
48:
49:
50:
51:
52:
53:
54:
55:
56:
57:
58:
59:
60:
61:
62:
63:
64:
65:
66:
67:
68:
69:
70:
71:
72:
73:
74:
75:
76:
77:
78:
79:
80:
81:
82:
83:
84:
85:
86:
87:
88:
89:
90:
91:
92:
93:
94:
95:
96:
97:
98:
99:
100:
101:
102:
103:
104:
105:
106:
107:
108:
109:
110:
111:
112:
113:
114:
115:
116:
117:
118:
119:
120:
121:
122:
123:
124:
125:
126:
127:
128:
129:
130:
131:
132:
133:
134:
135:
136:
137:
138:
139:
140:
141:
142:
143:
144:
145:
146:
147:
148:
149:
150:
151:
152:
153:
154:
155:
unit mCards;

interface
uses mStack;

const
  CARDS_PER_DECK = 32;

type
  TCardSuit = (csDiamonds, csHearts, csSpades, csClubs);

  TCard = class
    private
      fSuit: TCardSuit;
      fValue: cardinal;
      fPoints: cardinal; //! Ass kann eins oder elf sein
      fImageIndex: cardinal; // wird i.V.m. einer TImageList verwendet
    public
      constructor create(value: cardinal; suit: TCardSuit; points: cardinal;
        image: cardinal);
      //destructor destroy(); override;
      property suit: TCardSuit read fSuit;
      property value: cardinal read fValue;
      property points: cardinal read fPoints;
      property imageIndex: cardinal read fImageIndex;
    end;

  TCardDeck = class
    private
      fCards: TStack;
      fCount: cardinal;
    public
      constructor create();
      destructor destroy();
      procedure shuffle();
      function draw(): TCard;
      procedure add(const card: TCard);
      property count: cardinal read fCount;
  end;

implementation
uses sysutils;


constructor TCard.create(value: cardinal; suit: TCardSuit; points: cardinal;
        image: cardinal);
begin
  inherited create();
  fValue       := value;
  fSuit       := suit;
  fPoints     := points;
  fImageIndex := image;
end;


constructor TCardDeck.create();
begin
  inherited;
  fCount := 0;
  fCards := TStack.create();
  // Anmerkung: Ich kenne mich nicht mit Kartenwerten aus :)
  // Karo
  add(TCard.create(1, csDiamonds, 10)); // Ass
  add(TCard.create(7, csDiamonds, 71));
  add(TCard.create(8, csDiamonds, 82));
  add(TCard.create(9, csDiamonds, 93));
  add(TCard.create(10, csDiamonds, 104));
  add(TCard.create(10, csDiamonds, 105)); // Bube
  add(TCard.create(10, csDiamonds, 106)); // Dame
  add(TCard.create(10, csDiamonds, 107)); // König

  // Herz
  add(TCard.create(1, csHearts, 18)); // Ass
  add(TCard.create(7, csHearts, 79));
  add(TCard.create(8, csHearts, 810));
  add(TCard.create(9, csHearts, 911));
  add(TCard.create(10, csHearts, 1012));
  add(TCard.create(10, csHearts, 1013)); // Bube
  add(TCard.create(10, csHearts, 1014)); // Dame
  add(TCard.create(10, csHearts, 1015)); // König

  // Pik
  add(TCard.create(1, csSpades, 116)); // Ass
  add(TCard.create(7, csSpades, 717));
  add(TCard.create(8, csSpades, 818));
  add(TCard.create(9, csSpades, 919));
  add(TCard.create(10, csSpades, 1020));
  add(TCard.create(10, csSpades, 1021)); // Bube
  add(TCard.create(10, csSpades, 1022)); // Dame
  add(TCard.create(10, csSpades, 1023)); // König

  // Kreuz
  add(TCard.create(1, csClubs, 124)); // Ass
  add(TCard.create(7, csClubs, 725));
  add(TCard.create(8, csClubs, 826));
  add(TCard.create(9, csClubs, 927));
  add(TCard.create(10, csClubs, 1028));
  add(TCard.create(10, csClubs, 1029)); // Bube
  add(TCard.create(10, csClubs, 1030)); // Dame
  add(TCard.create(10, csClubs, 1031)); // König
end;

destructor TCardDeck.destroy;
begin
  fCards.Free();
  inherited;
end;


procedure TCardDeck.shuffle;
var aCards: array of TCard;
    i, randomPosition: integer;
begin
  if fCount = 0 then exit();

  // Hilfsarray vorbereiten
  setLength(aCards, fCount);
  for i := 0 to fCount - 1 do
    aCards[i] := nil;
  randomize();

  // 1. jede Karte vom Stack holen
  // 2. eine noch freie(nil) Position im Array suchen und Karte dort einfügen
  // 3. Karte vom Stack entfernen
  for i  := 0 to fCount - 1 do
  begin
    repeat
      randomPosition := random(fCount);
    until aCards[randomPosition] = nil;
    aCards[randomPosition] := TCard(fCards.top);
    fcards.pop();
  end;

  // gemischtes Deck wieder auf den Stack schieben
  for i := 0 to fCount - 1 do
    fCards.push(aCards[i]);
end;

procedure TCardDeck.add(const card: TCard);
begin
  fCards.push(card);
  inc(fCount);
end;

function TCardDeck.draw(): TCard;
begin
  if fCount > 0 then begin
    result := TCard(fCards.top);
    fCards.pop();
    dec(fCount);
  end else
    result := nil;
end;

end.


Statt auf einen Stack (speziell diese Implementation) würde ich lieber auf eine doppelt verkettete Liste oder besser zugreifen. Die Steinzeit ist vorbei. Musst Du wirklich damit arbeiten?
Einloggen, um Attachments anzusehen!
steve110 Threadstarter
Hält's aus hier
Beiträge: 14



BeitragVerfasst: Di 06.01.09 15:09 
Hallo...
auch wenn du es vielleicht nicht hören willst, DANKESCHÖN! Ich wollte allerding nicht dass du mir das ganze Spiel hier hochlädst, wir sollen das Spiel noch gar nicht machen, ich sollte zuerst die Klassen TCard, TStack, TNode, und TCarDeck in Delphi implementieren...

Dein Quelltext ist mir auch etwas zu kompliziert (tut mir Leid) vielleicht kannst du mir nur zeigen (anhand EINER Klasse) wie und wo man die Klassen implemtiert!!

Die anderen Klassen implemetiere ich dann (Die Klassen habe ich weiter oben schon mal als Grafik angehangen...)

Danke trotzdem :oops: :oops: :oops:
jaenicke
ontopic starontopic starontopic starontopic starontopic starontopic starontopic starofftopic star
Beiträge: 19312
Erhaltene Danke: 1747

W11 x64 (Chrome, Edge)
Delphi 11 Pro, Oxygene, C# (VS 2022), JS/HTML, Java (NB), PHP, Lazarus
BeitragVerfasst: Di 06.01.09 15:20 
Also wo du die Klassen implementieren musst kann doch eigentlich nicht das Problem sein, da hast du ja die Vorgabe, in der das steht.
Und wie das geht siehst du doch in dem Beispiel, das dir gerade gepostet wurde.

Dass du selbst irgendetwas gemacht hast, kann ich bisher nicht erkennen. :roll:
lincore
Hält's aus hier
Beiträge: 15

Kubuntu 8.04, Debian lenny, Windows XP, Windows Vista
Delphi 2009, C++, Python, Lua
BeitragVerfasst: Di 06.01.09 15:55 
Okay... Ich werde dir noch ein paar Hinweise geben:
Wie Du an meinem Beispiel siehst habe ich bereits drei Typen für dich implementiert (kein ganzes Spiel), nämlich
  • TCardSuit (Kartenfarben)
  • TCard (eine Karte)
  • TCardDeck (ein ganzes Kartenspiel)

TCardDeck kapselt "deinen" TStack, so wie dein Brustkorb dein Herz vor äußeren Zugriffen schützt. Wenn dem nicht so wäre, hättest Du offensichtlich ein Problem. Wenn Du nicht weißt, was ein Stack ist, dann suche bei Wikipedia mal nach "Kellerspeicher". Deine TStack-Klasse verwaltet einen Stack von TObjects. Und weil jede Klasse immer auch ein Nachfahre von TObject ist, kannst Du alles auf den Stack packen was Du willst; in diesem Fall also Spielkarten. Wenn Du das tust, vergisst Delphi aber augenblicklich, dass Du etwas anderes als ein TObject raufgeschoben hast. Daher benutzt man folgendes Konstrukt, um Delphi wieder daran zu erinnern: TCard(stack). Jetzt weiß Delphi, dass Du statt eines TObjects eine TCard haben möchtest.

Ich habe TCardDeck die Methoden add (hinzufügen) und draw (ziehen) verpasst, die sich der Methoden push, pop und top des Stacks bedienen. Die einzige Methode, die ein wenig komplizierter aussieht als der Rest ist shuffle (mischen).
Hier benutze ich ein Array, das die selbe Größe hat wie die das Deck Karten hat. Ich ziehe nacheinander eine Karte vom Stack (top, dann pop), und bestimme dann eine zufällige Position innerhalb des Arrays. Wenn diese Position noch frei ist (also nil), wird die Karte dorthin verfrachtet, ansonsten wird die nächste zufällige Position generiert uswusf.
Schließlich habe ich ein gemischtes Deck im Array und lege die Karten eine nach der anderen wieder auf den Stack (push).
Dann gibts natürlich noch den Konstruktor create() des Kartenstapels, der gleichzeitig auch die 32 Karten hinzufügt.
Wenn Du bereits eine Instanz von TCardDeck erstellt hast (deck := TCardDeck.create();), kannst Du jederzeit ein neues Spiel beginnen, indem Du create direkt aufrufst (deck.create(); (Unsauber, aber was solls)).
Übrigens: In dem Interface, dass Du als jpeg hochgeladen hast, hatte deine TCard ein TImage als Eigenschaft. Ich habe das geändert und einen Zahlenwert namens ImageIndex daraus gemacht. Das ist weitaus effizienter. Schau dir mal die TImageList genauer an, denn genau dafür ist dieser Index da.

Falls Du nun immer noch nicht weißt wie Du deinen Kram erledigen sollst, verweise ich dich auf den Delphi Crashkurs. Es ist offensichtlich, dass entweder dein Lehrer oder Du Mist gebaut habt. Wenn Du es nicht warst: Tut mir leid für dich.

Bis dann,
lincore

PS: Wenn Du konkrete Fragen hast, gibts auch konkrete Antworten, sonst musst Du allein klar kommen.