0

I am completely confused on how to adjust spaces for the game board. Once the game board is 4 x 4, the board becomes like a pyramid.

Here is my code:

/**
 * fifteen.c
 *
 * Computer Science 50
 * Problem Set 3
 *
 * Implements Game of Fifteen (generalized to d x d).
 *
 * Usage: fifteen d
 *
 * whereby the board's dimensions are to be d x d,
 * where d must be in [DIM_MIN,DIM_MAX]
 *
 * Note that usleep is obsolete, but it offers more granularity than
 * sleep and is simpler to use than nanosleep; `man usleep` for more.
 */

#define _XOPEN_SOURCE 500

#include <cs50.h>
#include <stdio.h>
#include <stdlib.h>
#include <unistd.h>

// constants
#define DIM_MIN 3
#define DIM_MAX 9

// board
int board[DIM_MAX][DIM_MAX];

// dimensions
int d;

// prototypes
void clear(void);
void greet(void);
void init(void);
void draw(void);
bool move(int tile);
bool won(void);

int main(int argc, string argv[])
{
    // ensure proper usage
    if (argc != 2)
    {
        printf("Usage: fifteen d\n");
        return 1;
    }

    // ensure valid dimensions
    d = atoi(argv[1]);
    if (d < DIM_MIN || d > DIM_MAX)
    {
        printf("Board must be between %i x %i and %i x %i, inclusive.\n",
            DIM_MIN, DIM_MIN, DIM_MAX, DIM_MAX);
        return 2;
    }

    // open log
    FILE* file = fopen("log.txt", "w");
    if (file == NULL)
    {
        return 3;
    }

    // greet user with instructions
    greet();

    // initialize the board
    init();

    // accept moves until game is won
    while (true)
    {
        // clear the screen
        clear();

        // draw the current state of the board
        draw();

        // log the current state of the board (for testing)
        for (int i = 0; i < d; i++)
        {
            for (int j = 0; j < d; j++)
            {
                fprintf(file, "%i", board[i][j]);
                if (j < d - 1)
                {
                    fprintf(file, "|");
                }
            }
            fprintf(file, "\n");
        }
        fflush(file);

        // check for win
        if (won())
        {
            printf("ftw!\n");
            break;
        }

        // prompt for move
        printf("Tile to move: ");
        int tile = GetInt();

        // quit if user inputs 0 (for testing)
        if (tile == 0)
        {
            break;
        }

        // log move (for testing)
        fprintf(file, "%i\n", tile);
        fflush(file);

        // move if possible, else report illegality
        if (!move(tile))
        {
            printf("\nIllegal move.\n");
            usleep(500000);
        }

        // sleep thread for animation's sake
        usleep(500000);
    }

    // close log
    fclose(file);

    // success
    return 0;
}

/**
 * Clears screen using ANSI escape sequences.
 */
void clear(void)
{
    printf("\033[2J");
    printf("\033[%d;%dH", 0, 0);
}

/**
 * Greets player.
 */
void greet(void)
{
    clear();
    printf("WELCOME TO GAME OF FIFTEEN\n");
    usleep(2000000);
}

/**
 * Initializes the game's board with tiles numbered 1 through d*d - 1
 * (i.e., fills 2D array with values but does not actually print them).  
 */
void init(void)
{   
    // largest number in gameboard
    int currentNum = (d * d) - 1;

    // loop for rows
    for (int j = 0; j < d; j++)
    {
        // loop for a single row
        for (int i = 0; i < d; i++)
        {
            // number decreases by 1 every time
            board[j][i] = currentNum;
            currentNum--;
            // if board is at final iteration
            if (((j == d - 1) && (i == d - 1)))
            {
                //  set the last number of the board to 0
                board[j][i] = 0;
            }
        }
    }

    // if d is even
    if ((d % 2) == 0)
    {
        // switch numbers 2 and 1
        board[d - 1][d - 2] = 2;
        board[d - 1][d - 3] = 1;
    }
}

/**
 * Prints the board in its current state.
 */
void draw(void)
{
    // loop for rows
    for (int j = 0; j < d; j++)
    {
        // loop for a single row
        for (int i = 0; i < d; i++)
        {
            // if the board loop is not at 0
            if (board[j][i] != 0)
            {
                // print the corresponding number
                printf("%i", board[j][i]);
                printf(" ");
            }
            // if board loop is at 0
            else
            {
                // print _
                printf("_ ");
            }
        }
        // new line after every individual row loop
        printf("\n");
    }
}

/**
 * If tile borders empty space, moves tile and returns true, else
 * returns false. 
 */
bool move(int tile)
{
    // cycle through board, find location of tile
    for (int j = 0; j < d; j++)
    {
        for (int i = 0; i < d; i++)
        {
            // check possible adjacent locations of the empty space
            if (board[j][i] == tile)
            {
                for (int k = 0; k < d; k++)
                {
                    for (int l = 0; l < d; l++)
                    {
                        if(board[k][l] == 0)
                        {
                            board[k][l] = tile;
                        }
                    }
                }

                board[j][i] = 0;
                return true;
            }
        }
    }
    return false;
}

/**
 * Returns true if game is won (i.e., board is in winning configuration), 
 * else false.
 */
bool won(void)
{
    // convert the 2-dimensional array of the board to a single dimension array
    int boardVals[d * d];
    int boardCounter = 0;

    for (int j = 0; j < d; j++)
    {
        for (int i = 0; i < d; i++)
        {
           boardVals[boardCounter] = board[j][i];
           boardCounter++;
        }
    }

    // if board is in order
    for (int l = 0; l < ((d * d) - 1); l++)
    {
        if (l != 0)
        {
            if (boardVals[l] < boardVals[l - 1])
            {
                return false;
            }
        }
    }
    return true;
}

Pic

2

"Give a man a fish and you feed him for a day. Teach him to fish and you feed him for a lifetime."

You are currently printing out the tile values with %i as the placeholder for the tile in your statement printf("%i", board[j][i]); Instead, you need to change that placeholder to include formatting. You can actually specify how many columns to use to print something.

IF you google printf format specifiers, you can find everything you need to format printf output. But here's one that covers most of it: http://www.codingunit.com/printf-format-specifiers-format-conversions-and-formatted-output

If this answers your question, please click on the check mark to accept. Let's keep up on forum maintenance. ;-)

1

While printing the board use

printf("%2d   ",board[i][j]); 

that will do..

You must log in to answer this question.

Not the answer you're looking for? Browse other questions tagged .