High Score File I/O

K

kyle christian

I am trying to save the high scores of a game I made. Now Im stumped on
trying to search through the file. Should I use a string, array, or one of
the STL containers to manipulate the information read from the file?

I have tried the
stringname.find("Name");

This only returns the first occurence, and doesn't look for other
occurences.

I got better results just using
if(Name = = NewName)


The file is a simple record like so:

Name wins loses //where wins and loses are int's
Bob 1 0 //example of format

Its to be like an old Pac-Man game record keeper.
I want to convert the name into lowercase and check to make sure only one
name is present in the file. If more than one name erase the others
otherwise check to see if WinsOnFile < CurrentWins.
If so record the new high score to the appropriate name.

This will only hold 10 high scores for different people.

Any thoughts would be helpful,
thanks
 
C

Christopher Pisz

kyle christian said:
I am trying to save the high scores of a game I made. Now Im stumped on
trying to search through the file. Should I use a string, array, or one of
the STL containers to manipulate the information read from the file?

I have tried the
stringname.find("Name");

This only returns the first occurence, and doesn't look for other
occurences.

I got better results just using
if(Name = = NewName)


The file is a simple record like so:

Name wins loses //where wins and loses are int's
Bob 1 0 //example of format

Its to be like an old Pac-Man game record keeper.
I want to convert the name into lowercase and check to make sure only one
name is present in the file. If more than one name erase the others
otherwise check to see if WinsOnFile < CurrentWins.
If so record the new high score to the appropriate name.

This will only hold 10 high scores for different people.



std::string has all the functionality you need for this:

Read the file into a string.
Before writing a high score see if the name exists.
If so, move to the wins and losses part of the record
use std::string replace, or another one of its methods to replace wins and
losses for that name.
Write the string back to the file.
Done.

If you abide by that algorithm, I don't see more than one occurence of the
name ever being in the file.
If for some other reason it is than you can search in a loop until no
occurences are found. std::string has overloaded find methods that can take
an index to start from.

If you want to be more eligent, you could make a record class that holds
name, wins and losses. Then give it serialize and deserialize methods, which
read and write one line of text as a record. Provide a functor that returns
the name of the record. Then when the game loads you can read in the file
using a container of records searchable by name (std::map) . When the game
is over or when it exits. Write the map of records over the previous file.

gl,
Christopher
 
J

Jim Langston

kyle said:
I am trying to save the high scores of a game I made. Now Im stumped
on trying to search through the file. Should I use a string, array,
or one of the STL containers to manipulate the information read from
the file?
I have tried the
stringname.find("Name");

This only returns the first occurence, and doesn't look for other
occurences.

I got better results just using
if(Name = = NewName)


The file is a simple record like so:

Name wins loses //where wins and loses are int's
Bob 1 0 //example of format

Its to be like an old Pac-Man game record keeper.
I want to convert the name into lowercase and check to make sure only
one name is present in the file. If more than one name erase the
others otherwise check to see if WinsOnFile < CurrentWins.
If so record the new high score to the appropriate name.

This will only hold 10 high scores for different people.

Any thoughts would be helpful,
thanks


One easy way is to use a std::map. std::map has the advantage that if you
use code like this:

std::map<std::string, MyClass> Data;
Data["bob"] /*...*/
If "bob" doesn't already exist in the map, it will add it. Otherwise it
will refer to the one that already exists. For simplicity sake lets say you
were just recording number of wins.

std::map<std::string, int> Scores;
std::string Name;
int Wins;
/* Read name and Wins from file */
Scores[name] += Wins;

Now if there are 20 "Bob"s in the file, they will be added to one Score for
wins.

Things to do:
1. Convert name read to lowercase.
2. Store a structure or std::pair to represent wins and loses and not just
loses.
 
K

kyle christian

Thanks for the help guys. The map container works good. Heres what I got
after reading up on it so far:


//Gets user Name to use in file

void BlackJack::GetName(){
cout << "Enter your name: ";
cin >> Name;
UserInput();
}


//Adds record to the file

void BlackJack::RecordStats(){
ofstream InFile("c:/Dev-Cpp/text.txt", ios::app);
if(InFile){InFile << Name << " " << Won;}
else if(!InFile) { cout << "\nCouldn't open file";}
InFile.close();

}


void BlackJack::GetStats(){


//Write stats to file

RecordStats();

//Read the file into the map if open for reading

ifstream OutFile("c:/Dev-Cpp/text.txt");
if(!OutFile){
cout << "\nCouldn't Read File";
}
else{
map<string, int>Score;
string N;
int W;


while(!OutFile.eof()){
OutFile >> N >> W;
Score.insert(make_pair(N,W));
}
OutFile.close();

//Since the map only allows one key with the same name and if two keys of
the same name, it takes the key with the greater value by default
//I simply read the file into the map container so it could organize it for
me, and wrote it back to the file. There is probably a better way
//just dont know it yet


map<string, int>::iterator itr,itr1;
itr = Score.begin();

ofstream InFile("c:/Dev-Cpp/text.txt");
while(itr != Score.end()){
InFile << itr->first << " " << itr->second << endl;
itr++;
}
InFile.close();

itr1 = Score.begin();
while(itr1 != Score.end()){
cout << itr1->first << " wins: " << itr1->second << endl;
itr1++;
}

}
}
void BlackJack::DisplayStats(){
cout << " VarWin: " << Won << " VarLost: " << Lost << endl;
GetStats();
}


Only thing I lack now is limiting the size to only the top 10 scores and
instead of the list being organized alphabetically I need the map to be
organized according to highest score.









Jim Langston said:
kyle said:
I am trying to save the high scores of a game I made. Now Im stumped
on trying to search through the file. Should I use a string, array,
or one of the STL containers to manipulate the information read from
the file?
I have tried the
stringname.find("Name");

This only returns the first occurence, and doesn't look for other
occurences.

I got better results just using
if(Name = = NewName)


The file is a simple record like so:

Name wins loses //where wins and loses are int's
Bob 1 0 //example of format

Its to be like an old Pac-Man game record keeper.
I want to convert the name into lowercase and check to make sure only
one name is present in the file. If more than one name erase the
others otherwise check to see if WinsOnFile < CurrentWins.
If so record the new high score to the appropriate name.

This will only hold 10 high scores for different people.

Any thoughts would be helpful,
thanks


One easy way is to use a std::map. std::map has the advantage that if you
use code like this:

std::map<std::string, MyClass> Data;
Data["bob"] /*...*/
If "bob" doesn't already exist in the map, it will add it. Otherwise it
will refer to the one that already exists. For simplicity sake lets say
you were just recording number of wins.

std::map<std::string, int> Scores;
std::string Name;
int Wins;
/* Read name and Wins from file */
Scores[name] += Wins;

Now if there are 20 "Bob"s in the file, they will be added to one Score
for wins.

Things to do:
1. Convert name read to lowercase.
2. Store a structure or std::pair to represent wins and loses and not just
loses.
 
C

Christopher Pisz

[snip]
Only thing I lack now is limiting the size to only the top 10 scores and
instead of the list being organized alphabetically I need the map to be
organized according to highest score.
[snip]

if( mymap.size() > 10 )
{
// use some combination of mymap.find() and mymap.erase()
}

To sort by high score. Again, use std::sort and a mymap functor if needed.

,
Chris
 

Ask a Question

Want to reply to this thread or ask your own question?

You'll need to choose a username for the site, which only take a couple of moments. After that, you can post your question and our members will help you out.

Ask a Question

Members online

No members online now.

Forum statistics

Threads
473,774
Messages
2,569,596
Members
45,135
Latest member
VeronaShap
Top