user3348907
user3348907

Reputation: 41

Printing out to file each Game of life generations

Hey guys i need help with a fstream print out for each Game of life generations. Currently it is only printing out the initial grid with all dead cells.

Here is my print function, and what i attempted.

void print(bool mat[][Row]) //Prints matrix to screen
{
     ofstream myfile;
     myfile.open("GameOfLife.txt");
     cout << setw(3) << " ";
     myfile<< setw(3) << " ";
     for (int p = 0; 5*p < Row; p++) cout << setw(5) << 5*p+1;
     for (int p = 0; 5*p < Row; p++) myfile << setw(5) << 5*p+1;
     cout << endl;
     myfile<< endl;
     for (int m = 0; m < Col; m++)
     {
         cout << setw(3) << m+1;
         myfile<< setw(3) << m+1;
         for (int n = 0; n < Row; n++)
         {
             if (mat[m][n]) cout << "\xDB";
             else cout << /*"\xB1"*/"-";
             if (mat[m][n]) myfile << "\xDB";
             else myfile << /*"\xB1"*/"-";
         }
         cout << endl;
         myfile<<endl;
     }
}

Here is where i call it in main

 do //Keep updating new generations
    {
        cout<<"Generation: "<<genX<<endl;
        //myfile<<"Generation: "<<genX<<endl;
        genX++;
        clear(next);
        calculate(now, next);
        swap(now, next);
        print(now);
        cin>>cont;      
    }while(cont == -1);

Was wondering how i can get it to print each generation to the file.

edit:added whole code

#include <iostream>
#include <fstream>
#include <iomanip>
#define Col 15 //Col size
#define Row 13 //Row size
using namespace std;

void clear(bool mat[][Row]) //resets with all dead cells
{
    for (int m = 0; m < Col; m++)
    {
        for (int n = 0; n < Row; n++)
            mat[m][n] = 0;
    }
}

void print(bool mat[][Row]) //Prints matrix to screen
{
     ofstream myfile;
     myfile.open("GameOfLife.txt");
     cout << setw(3) << " ";
     myfile<< setw(3) << " ";
     for (int p = 0; 5*p < Row; p++) cout << setw(5) << 5*p+1;
     for (int p = 0; 5*p < Row; p++) myfile << setw(5) << 5*p+1;
     cout << endl;
     myfile<< endl;
     for (int m = 0; m < Col; m++)
     {
         cout << setw(3) << m+1;
         myfile<< setw(3) << m+1;
         for (int n = 0; n < Row; n++)
         {
             if (mat[m][n]) cout << "\xDB";
             else cout << /*"\xB1"*/"-";
             if (mat[m][n]) myfile << "\xDB";
             else myfile << /*"\xB1"*/"-";
         }
         cout << endl;
         myfile<<endl;
     }
}

/*void print2(unsigned int mat[][Row]) //Prints matrix to screen
{
     for (int m = 0; m < Col; m++)
     {
         for (int n = 0; n < Row; n++)
             cout << mat[m][n] << " ";
         cout << endl;
     }
}*/

void calculate(bool mata[][Row], bool matb[][Row])
{
     unsigned int neighbors;
     for (int m = 0; m < Col; m++)
     {
         for (int n = 0; n < Row; n++)
         {
             neighbors = 0;
             //Begin counting number of neighbors:
             if (mata[m%Col-1][n%Row-1] == 1) neighbors += 1;
             if (mata[m%Col-1][n%Row] == 1) neighbors += 1;
             if (mata[m%Col-1][n%Row+1] == 1) neighbors += 1;
             if (mata[m%Col][n%Row-1] == 1) neighbors += 1;
             if (mata[m%Col][n%Row+1] == 1) neighbors += 1;
             if (mata[m%Col+1][n%Row-1] == 1) neighbors += 1;
             if (mata[m%Col+1][n%Row] == 1) neighbors += 1;
             if (mata[m%Col+1][n%Row+1] == 1) neighbors += 1;

             //Apply rules to the cell:
             if (mata[m%Col][n%Row] == 1 && neighbors < 2)
                matb[m%Col][n%Row] = 0;
             else if (mata[m%Col][n%Row] == 1 && neighbors > 3)
                matb[m%Col][n%Row] = 0;
             else if (mata[m%Col][n%Row] == 1 && (neighbors == 2 || neighbors == 3))
                matb[m%Col][n%Row] = 1;
             else if (mata[m%Col][n%Row] == 0 && neighbors == 3)
                matb[m%Col][n%Row] = 1;
         }
     }
}

void swap(bool mata[][Row], bool matb[][Row]) //Replaces first matrix with second
{
     for (int m = 0; m < Col; m++)
     {
         for (int n = 0; n < Row; n++)
             mata[m%Col][n%Row] = matb[m%Col][n%Row];
     }
}


int main()
{
    bool now[Col][Row], next[Col][Row]; //Creates now and then matrixes
    int x, y, cont; //Used for user input

    cout << left << "Welcome to Conway's Game of Life." << endl << endl;
    cout << "The Rules of Life:" << endl;
    cout << "1.cell with less than 2 neighbors die" << endl;
    cout << "2. cell with more than three neighbors dies" << endl;
    cout << "3. cell with two or three neighbors lives stays alive." << endl;
    cout << "4.dead cell with exactly three live neighbors comes to life." << endl << endl;
    cout << "To play: Press any key to begin. Enter the column and row of a cell to make \nalive, separated by a space. ";
    cout << "enter 1 1 to fill grid with dead cells, enter \"-1\" to begin the \nsimulation. Then enter any number to continue or \"-1\" to move to next generation." << endl;
    cin.get();

    clear(now);
    print(now);

    do //Get initial state
    {
        cin >> x;
        if (x == -1) break; //User is done inputting
        cin >> y;
        now[y-1][x-1] = 1; //Sets cell to alive
        print(now); //Updates screen
    }while(x != -1);
    int genX=1;
    do //Keep updating new generations
    {
        cout<<"Generation: "<<genX<<endl;
        //myfile<<"Generation: "<<genX<<endl;
        genX++;
        clear(next);
        calculate(now, next);
        swap(now, next);
        print(now);
        cin>>cont;      
    }while(cont == -1);

    return 0;
} 

Upvotes: 0

Views: 330

Answers (1)

molbdnilo
molbdnilo

Reputation: 66451

Every time you open a file, it is truncated, unless you open for appending.

Since you want to create a new file on each run but keep appending to it, the cleanest way is to pass the open file to the print method. Plus, it doesn't have to be a file, you can print to any std::ostream.
And, as an added bonus, all your duplication for printing to cout also disappears, and you can get rid of one output or the other by changing just one line in main.

void print(ostream& stream, bool mat[][Row]) //Prints matrix to stream
{
     stream << setw(3) << " ";
     for (int p = 0; 5*p < Row; p++) 
         stream << setw(5) << 5*p+1;
     stream << endl;
     for (int m = 0; m < Col; m++)
     {
         stream << setw(3) << m+1;
         for (int n = 0; n < Row; n++)
         {
             if (mat[m][n]) 
                 stream << "\xDB";
             else 
                 stream << "-";
         }
         myfile << endl;
     }
}

Here is how to use it in main

ofstream myfile("GameOfLife.txt");
do 
{
    // ... as before ...
    print(cout, now);     // Print to stdout
    print(myfile, now);   // print to the file
    cin >> cont;      
} while (cont == -1);

In order for anyone to figure out why your final generation is all dead, you would need to provide a sample first generation.

Upvotes: 2

Related Questions