PDA

Archiv verlassen und diese Seite im Standarddesign anzeigen : c++ highscore



eRaSeR!
12.04.2009, 19:16
hey wir müssen als hausaufgabe schiffe versenken mit nem ranking machen. am anfang soll der highscore angezeigt werden und am ende dann nochmal mit dem eigenen namen eben drin

schiffe versenken funzt soweit nur jetzt arbeite ich noch an nem anderen projekt also nur highscore

mein bisheriger code:


#include <iostream>
#include <fstream>
#include <string.h>

using namespace std;
string name,eingabe,zeile;

/*
struct highscore
{
int score;
string name2;
} ;
*/
int main()
{
cout<<"schreiben oder lesen: ";
cin>>eingabe;
if(eingabe=="schreiben")
{
ofstream lol;
lol.open ("joo.txt", std::ios::app );

cout<<"bitte name eingeben: ";
cin>>name;

lol<<"\n"<<name;

lol.close();
}

else if(eingabe=="lesen")
{
ifstream lol ("joo.txt");

while (lol.eof()==false )
{
getline (lol,zeile);
cout << zeile << endl;
}
system("pause>>nul");
}
}

wie man oben sieht hab ich iwie versucht struct zu benutzen. weil die "liste" funzt soweit eben nur mit namen. also wer zuletzt gespielt hat. jetzt sollen noch die versuche dazu kommen die man gebraucht hat bis der gegner tot war. und des ganze soll dann verglichen werden und der mit dem niedrigsten wert soll ganz oben stehn mit ner 1. davor also so ne toplist
zusammengefasst: wie kann ich den eingegebenen spielernamen in kombination mit dem "score" in ne variable speichern und die variablen vergleichen?
danke schonmal für die hilfe :)

mfg eraser

sp1nny
12.04.2009, 20:07
Irgendwie wird mir nicht ganz klar wie du das jetzt genau machen willst. Was mir so auffällt: Beim Include reicht <string> und benutz am besten ein SwitchCase anstatt von If-Abfragen, das ist viel übersichtlicher ^^. Und du kannst auch Structs vergleichen, dafür brauchst du nicht Extravariablen. Desweiteren empfehle ich dir für deine ganzen Bennenungen aussagekräftige Namen zu verwenden und nicht "lol", das trägt zur Übersicht weiter bei.

sp33dwalker
12.04.2009, 20:20
benutz doch beim menü zahlen zum auswählen statt wörter tippen :)

blackberry
12.04.2009, 20:42
struct highscore
{
int score;
string name2;
} ;

Ein Objekt der Klasse string wirst du wohl kaum in einer Datei speichern können, da dieses Zeiger auf die Methoden der Klasse und Attribute enthält, aber nicht den "string", welcher durch dieses Objekt representiert wird. (obgleich auch ein Zeiger auf die Speicheradresse der Zeichenkette sich in diesem Objekt befindet, wird diese Adresse jene Zeichenkette beim nächsten Programmaufruf nicht mehr beherbergen)

Ich kann mal kurz sowas schreiben.
Gib mir 10-20 Minuten (ich editiere diesen Beitrag dann)!


mfG. BlackBerry

EDIT:


blackberry@system:~/Desktop$ g++ -o eraser eraser.cpp
blackberry@system:~/Desktop$ ./eraser
schreiben oder lesen: schreiben
bitte name eingeben: BlackBerry
MyScore = 18
blackberry@system:~/Desktop$ ./eraser
schreiben oder lesen: schreiben
bitte name eingeben: BlueBerry
MyScore = 20
blackberry@system:~/Desktop$ ./eraser
schreiben oder lesen: schreiben
bitte name eingeben: OrangeBerry
MyScore = 24
blackberry@system:~/Desktop$ ./eraser
schreiben oder lesen: schreiben
bitte name eingeben: GreenBerry
MyScore = 30
blackberry@system:~/Desktop$ ./eraser
schreiben oder lesen: lesen
Der Sieger ist: GreenBerry



#include <iostream>
#include <fstream>
#include <string.h>
#include <cstdlib> /* für (s)rand(...) */
#include <ctime> /* für time(...) - siehe unten */

using namespace std;
string name,eingabe,zeile;


struct highscore
{
int score;
char name[40]; /* char[40], nicht string */
} ;

int main()
{
cout<<"schreiben oder lesen: ";
cin>>eingabe;
if(eingabe=="schreiben")
{
ofstream lol;
lol.open ("joo.txt", std::ios::app );

cout<<"bitte name eingeben: ";
cin>>name;

/*
wir generieren eine pseudo-zufällige Punktezahl
TODO: diese Zahl berechnen oder vom Benutzer einlesen
*/
srand(time(NULL));
int myscore = rand() % 100;

/*
wir erstellen unsere Struktur und füllen diese mit der Punktezahl
*/
struct highscore h;
h.score = myscore;

/*
nur damit wir wissen welchen Punktestand der neue Benutzer hat...
*/
cout << "MyScore = " << myscore << "\n";

/*
wir füllen den Namen via strncat.
(wir benutzen strNcat um einen Bufferoverflow zu vermeiden)
*/
memset(h.name, 0, sizeof(h.name));
strncat(h.name, name.c_str(), sizeof(h.name));

/*
nun schreiben wir die Struktur in die Datei
TODO: bereits vorhandene Benutzer updaten
*/
lol.write((char *) &h, sizeof(struct highscore));

lol.close();
}

else if(eingabe=="lesen")
{
ifstream lol ("joo.txt");

/*
wir erstellen einen Array um unsere Strukturen zu speichern
wir benutzen die Elemente wie folgt:
[0] der momentan höchste "Score"
[1] zum Einlesen und Zwischenspeichern von Einträgen
*/
struct highscore h[2];

/*
unser momentan höchster Score; noch haben wir nichts eingelesen
*/
h[0].score = -1;

/*
loop...
*/
while (lol.eof()==false )
{
/*
wir füllen unsere Struktur...
*/
memset(&h[1], 0, sizeof(struct highscore));
lol.read((char *) &h[1], sizeof(struct highscore));

/*
wenn dieser Benutzer einen höheren Punktestand besitzt...
TODO: auch Benutzer mit gleicher Punktezahl berücksichtigen
*/
if (h[1].score > h[0].score)
{
/*
... machen wir diesen zum momentanen Sieger ;)
*/
h[0] = h[1];
}
}

/*
wenn der höchste Punktestand nicht -1 ist...
(also Einträge vorhanden waren)
*/
if (h[0].score != -1)
{
/*
Gewinner ausgeben...
*/
cout << "Der Sieger ist: " << h[0].name << "\n";
}
getc(stdin);
}
}

Ich hoffe das hilft dir weiter... ich habe versucht es in deinem Stil zu halten und ifstream/ofsteam zu verwenden (ich bin da mehr der fopen-Typ ;) ).

sp1nny
12.04.2009, 21:04
Also ich hätte es so gemacht mit dem speichern / laden vom Namen:



#include <iostream>

using namespace std;

int main()
{
cout<<"Was möchten sie tun?"<<endl;
cout<<"1 = Schreiben"<<endl;
cout<<"2 = Lesen"<<endl;

int eingabe;
cin>>eingabe;

char name[30];

switch(eingabe)
{
case 1:
{
cout<<"Bitte Namen eingeben: "<<endl;
cin>>name;

FILE* list;
list = fopen("list.txt","w");
fputs(name,list);
fclose(list);

break;
}
case 2:
{

FILE* list;
list = fopen("list.txt","r");
fgets(name,29,list);
fclose(list);

cout<<name<<endl;
cin.ignore();
cin.get();
}

}//switch


}//main

eRaSeR!
13.04.2009, 00:21
ok ty an euch 2 :) ich guckls mir morgen nomma an und versuchs selber mal in ner anderen aufgabe. muss mich noch rechtfertigen wegen der anfangs posts :P also...switch gefällt mir nich auch wenns "übersichtlicher" is wie viele meinen.. geschmackssache eben hab nich 1 und 0 verwendet in der if abfrage weil wir bissl hinterher sind und jetzt mal ein string menü machen sollten und bissl mit if/switch rumexperimentieren sollen. dass der code unsauber ist weiß ich auch. war in der schule und da hab ich nie bock auf sowas. daheim klappts besser :D ach und blackberry.. danke nochmal für die erklärungen in allem was du verändert hast mfg eraser

sp1nny
13.04.2009, 01:38
Ich kann dir sagen, dass du beim 1000000elseif das SwitchCase zu schätzen wissen wirst. :)

Cr4ckEye
15.04.2009, 20:28
Nun ich denke es kommt ganz auf die verwendung an. ich würde auch epfehlen switch/case statt elseif zu benutzen wenn man verschiedene Fälle unterscheiden will.
Aber für Additive Unterscheidungen ist if doch besser^^
Naja, jemand kann immer etwas besser machen :D

MfG

-[RiDER]-
17.04.2009, 01:41
Hi :D


int myscore = rand() % 100;

Ich will nichts bemängeln, verbessern oder ankreiden, ich möchte nur eine kleine Ergänzung anfügen:
If you want to generate a random integer between 1 and 10, you should always do it by using high-order bits, as in
j = 1 + (int) (10.0 * (rand() / (RAND_MAX + 1.0))); and never by anything resembling

j = 1 + (rand() % 10); (which uses lower-order bits).
Was da geschrieben steht in Numerical Recipes in C: The Art of Scientific Computing (William H. Press, Brian P. Flannery, Saul A. Teukolsky, William T. Vetterling; New York: Cambridge University Press, 1992 oder auch in der Linux Manpage rand(3).

GreetZ RiDER :D