Search algorithms for the 8-puzzle solution
Public Member Functions | Private Member Functions | Private Attributes
GameState Class Reference

Describes a single state in the 8-puzzle. More...

#include <GameState.hpp>

Collaboration diagram for GameState:

Public Member Functions

 GameState ()
 Default constructor, everything starts as 0 or NULL. More...
 
 GameState (string s)
 Creates a GameState from a string, where tile numbers are separated by spaces in a single line. More...
 
 GameState (const GameState &obj)
 Copy constructor of the class. More...
 
 GameState (GameState *previous, GameAction action)
 Creates a new state based on a given previous state and applying an action to it. More...
 
 ~GameState ()
 Destructor of GameState. More...
 
bool isValid (GameAction action)
 Checks whether an action is valid for this state. More...
 
bool operator== (const GameState &other) const
 Checks whether two GameState objects are equal. More...
 
int countInversions ()
 Counts the number of inversions in the puzzle. More...
 
bool isSolvable ()
 Check if the state is solvable. More...
 
bool operator< (const GameState &other) const
 Compares two GameState objects. More...
 
bool operator!= (const GameState &other) const
 Inequality operator for GameState. More...
 
int getDimension () const
 
string to_string () const
 Returns a multi-line string representation of the 8-puzzle board state. More...
 
string to_line_string () const
 Returns a single line string representation of the 8-puzzle board state. More...
 
int * find (int value)
 Finds the position of a tile in the board. More...
 
void setRepresentation (int **representation)
 
GameStategetParent () const
 
int getDepth () const
 

Private Member Functions

int * toIntArray (string s)
 Turns a string representation of an 8-puzzle into an array. More...
 

Private Attributes

int ** representation
 
int depth
 
int dimension
 
GameStateparent
 

Detailed Description

Describes a single state in the 8-puzzle.

Definition at line 18 of file GameState.hpp.

Constructor & Destructor Documentation

◆ GameState() [1/4]

GameState::GameState ( )
inline

Default constructor, everything starts as 0 or NULL.

Definition at line 60 of file GameState.hpp.

60  {
61  depth = dimension = 0;
62  representation = NULL;
63  parent = NULL;
64  }
int dimension
Definition: GameState.hpp:22
GameState * parent
Definition: GameState.hpp:23
int ** representation
Definition: GameState.hpp:21
Here is the caller graph for this function:

◆ GameState() [2/4]

GameState::GameState ( string  s)
inlineexplicit

Creates a GameState from a string, where tile numbers are separated by spaces in a single line.

Parameters
sstring representation on an 8-puzzle state

Definition at line 68 of file GameState.hpp.

68  {
69  depth = 0;
70  parent = NULL;
71 
72  // converts string to int[]
73  int *conversion = toIntArray(s);
74 
75  // calculates puzzle dimension from array size
76  dimension = sizeof(conversion) / sizeof(conversion[0]) + 1;
77 
78  // searches for duplicate numbers inside the array
79  for (int i = 0; i < dimension * dimension - 1; i ++) {
80  for (int j = i + 1; j < dimension * dimension; j ++) {
81  if (conversion[i] == conversion[j]) {
82  cout << conversion[i] << conversion[j] << i << j;
83  throw invalid_argument(s);
84  }
85  }
86  }
87 
88  // initializes array of arrays to keep the 8-puzzle state
89  representation = new int *[dimension];
90 
91  //iterates through rows and columns, adding the numbers converted from the input string
92  int val = 0;
93  for (int x = 0; x < dimension; x ++) {
94  representation[x] = new int[dimension]; // initialize inner arrays
95 
96  for (int y = 0; y < dimension; y ++) {
97  representation[x][y] = conversion[val ++];
98  }
99  }
100 
101  delete[] conversion;
102  }
int dimension
Definition: GameState.hpp:22
int * toIntArray(string s)
Turns a string representation of an 8-puzzle into an array.
Definition: GameState.hpp:28
GameState * parent
Definition: GameState.hpp:23
int ** representation
Definition: GameState.hpp:21

◆ GameState() [3/4]

GameState::GameState ( const GameState obj)
inline

Copy constructor of the class.

Parameters
objobject that will be copied

Definition at line 106 of file GameState.hpp.

106  {
107  dimension = obj.dimension;
108  depth = obj.depth;
109 
110  representation = new int *[dimension];
111 
112  for (int x = 0; x < dimension; x ++) {
113  representation[x] = new int[dimension];
114 
115  for (int y = 0; y < dimension; y ++) {
116  representation[x][y] = obj.representation[x][y];
117  }
118  }
119 
120  parent = obj.parent;
121  }
int dimension
Definition: GameState.hpp:22
GameState * parent
Definition: GameState.hpp:23
int ** representation
Definition: GameState.hpp:21

◆ GameState() [4/4]

GameState::GameState ( GameState previous,
GameAction  action 
)
inline

Creates a new state based on a given previous state and applying an action to it.

Parameters
previousthe previous state
actionthe action to be applied to the previous state

Definition at line 126 of file GameState.hpp.

126  {
127  //dimension is the same, depth is one lower, parent is the state passed in the argument
128  dimension = previous->dimension;
129  depth = previous->depth + 1;
130  parent = previous;
131  representation = new int *[dimension];
132 
133  // first, copy the state
134  for (int x = 0; x < dimension; x ++) {
135  representation[x] = new int[dimension];
136 
137  for (int y = 0; y < dimension; y ++) {
138  representation[x][y] = previous->representation[x][y];
139  }
140  }
141 
142  //find the 0
143  int *pos_0 = find(0);
144  int x = pos_0[0], y = pos_0[1];
145  delete[] pos_0;
146  int tmp = 0;
147 
148  // validate action
149  if (action != RIGHT and action != LEFT and action != UP and action != DOWN)
150  throw invalid_argument("No previous action to build the new GameState.");
151 
152  if (! isValid(action)) {
153  throw invalid_argument("Invalid action for current game state.");
154  }
155 
156  // move the 0 according to the given action
157  // keep the value of the tile where the 0 is being move to in tmp
158  switch (action) {
159  case RIGHT:tmp = previous->representation[x + 1][y];
160  representation[x + 1][y] = 0;
161  break;
162 
163  case LEFT:tmp = previous->representation[x - 1][y];
164  representation[x - 1][y] = 0;
165  break;
166 
167  case UP:tmp = previous->representation[x][y - 1];
168  representation[x][y - 1] = 0;
169  break;
170 
171  case DOWN:tmp = previous->representation[x][y + 1];
172  representation[x][y + 1] = 0;
173  break;
174  }
175 
176  //put the value in tmp where the 0 was
177  representation[x][y] = tmp;
178  }
int dimension
Definition: GameState.hpp:22
int * find(int value)
Finds the position of a tile in the board.
Definition: GameState.hpp:318
bool isValid(GameAction action)
Checks whether an action is valid for this state.
Definition: GameState.hpp:200
GameState * parent
Definition: GameState.hpp:23
int ** representation
Definition: GameState.hpp:21
Here is the call graph for this function:
Here is the caller graph for this function:

◆ ~GameState()

GameState::~GameState ( )
inline

Destructor of GameState.

Definition at line 181 of file GameState.hpp.

181  {
182  // erase inner arrays
183  // since the value of `dimension` is lost, calculate it here
184  int dim = sizeof(representation[0]) / sizeof(representation[0][0]) + 1;
185  for (int i = 0; i < dim; i ++)
186  delete[] representation[i];
187 
188  //erase outer array
189  delete[] representation;
190 
191  representation=NULL;
192  parent = NULL;
193  depth = dimension = 0;
194  }
int dimension
Definition: GameState.hpp:22
GameState * parent
Definition: GameState.hpp:23
int ** representation
Definition: GameState.hpp:21

Member Function Documentation

◆ countInversions()

int GameState::countInversions ( )
inline

Counts the number of inversions in the puzzle.

An inversion occurs whenever a number comes before a smaller number in the puzzle.

Returns
number of inversions in this states of the puzzle

Definition at line 233 of file GameState.hpp.

233  {
234  int inv_count = 0;
235 
236  int rasterDimension = dimension * dimension;
237  int *raster = new int[rasterDimension];
238 
239  int current = 0;
240  for (int x = 0; x < dimension; x ++) {
241  for (int y = 0; y < dimension; y ++) {
242  raster[current ++] = representation[x][y];
243  }
244  }
245 
246  for (int i = 0; i < rasterDimension - 1; i ++)
247  for (int j = i + 1; j < rasterDimension; j ++)
248  if (raster[i] != 0 and raster[j] != 0 and raster[i] > raster[j])
249  inv_count ++;
250 
251  delete[] raster;
252 
253  return inv_count;
254  }
int dimension
Definition: GameState.hpp:22
int ** representation
Definition: GameState.hpp:21
Here is the caller graph for this function:

◆ find()

int* GameState::find ( int  value)
inline

Finds the position of a tile in the board.

Parameters
valuethe value of the tile to look for
Returns
int array where [0] contains x position and [1] y position of the number

Definition at line 318 of file GameState.hpp.

318  {
319  for (int x = 0; x < dimension; x ++) {
320  for (int y = 0; y < dimension; y ++) {
321  if (representation[x][y] == value) return new int[2]{x, y};
322  }
323  }
324 
325  throw invalid_argument("Inexistent number.");
326  }
int dimension
Definition: GameState.hpp:22
int ** representation
Definition: GameState.hpp:21
Here is the caller graph for this function:

◆ getDepth()

int GameState::getDepth ( ) const
inline

Definition at line 339 of file GameState.hpp.

339  {
340  return depth;
341  }
Here is the caller graph for this function:

◆ getDimension()

int GameState::getDimension ( ) const
inline

Definition at line 284 of file GameState.hpp.

284  {
285  return dimension;
286  }
int dimension
Definition: GameState.hpp:22
Here is the caller graph for this function:

◆ getParent()

GameState* GameState::getParent ( ) const
inline

Definition at line 335 of file GameState.hpp.

335  {
336  return parent;
337  }
GameState * parent
Definition: GameState.hpp:23

◆ isSolvable()

bool GameState::isSolvable ( )
inline

Check if the state is solvable.

Returns
a state is solvable if the number of inversions in it is even.

Definition at line 258 of file GameState.hpp.

258  {
259  return countInversions() % 2 == 0;
260  }
int countInversions()
Counts the number of inversions in the puzzle.
Definition: GameState.hpp:233
Here is the call graph for this function:

◆ isValid()

bool GameState::isValid ( GameAction  action)
inline

Checks whether an action is valid for this state.

Actions are invalid if they'd move the 0 tile outside of the board.

Parameters
actionthe action to be validated
Returns
true if the action can be applied in this state, otherwise false

Definition at line 200 of file GameState.hpp.

200  {
201  if (action != RIGHT and action != LEFT and action != UP and action != DOWN)
202  return false;
203 
204  int *pos_0 = find(0);
205  int x = pos_0[0], y = pos_0[1];
206 
207  delete[] pos_0;
208 
209  return ! (action == RIGHT and x == dimension - 1 ||
210  action == LEFT and x == 0 ||
211  action == UP and y == 0 ||
212  action == DOWN and y == dimension - 1);
213  }
int dimension
Definition: GameState.hpp:22
int * find(int value)
Finds the position of a tile in the board.
Definition: GameState.hpp:318
Here is the call graph for this function:
Here is the caller graph for this function:

◆ operator!=()

bool GameState::operator!= ( const GameState other) const
inline

Inequality operator for GameState.

This is the negation of the equality operator.

Parameters
otherThe GameState to be compared to
Returns
false if equal, otherwise true

Definition at line 280 of file GameState.hpp.

280  {
281  return ! (*this == other);
282  }
Here is the call graph for this function:
Here is the caller graph for this function:

◆ operator<()

bool GameState::operator< ( const GameState other) const
inline

Compares two GameState objects.

Tile numbers are compared in order. If this[i,j] < other[i,j], this < other. This operator is useful in case objects need to be sorted inside a data structure, for example.

Parameters
otherThe GameState to be compared to
Returns
true if this < other, otherwise false

Definition at line 266 of file GameState.hpp.

266  {
267  if (dimension != other.dimension) throw invalid_argument("Puzzles of different dimensions aren't comparable");
268 
269  for (int x = 0; x < dimension; x ++) {
270  for (int y = 0; y < dimension; y ++) {
271  if (representation[x][y] < other.representation[x][y]) return true;
272  }
273  }
274  return false;
275  }
int dimension
Definition: GameState.hpp:22
int ** representation
Definition: GameState.hpp:21
Here is the caller graph for this function:

◆ operator==()

bool GameState::operator== ( const GameState other) const
inline

Checks whether two GameState objects are equal.

They are equal if they have the same board dimensions and the same values in the same positions of their board.

Parameters
otherThe GameState to be compared to
Returns
true if equal, otherwise false

Definition at line 219 of file GameState.hpp.

219  {
220  if (dimension != other.dimension) return false;
221 
222  for (int x = 0; x < dimension; x ++) {
223  for (int y = 0; y < dimension; y ++) {
224  if (representation[x][y] != other.representation[x][y]) return false;
225  }
226  }
227  return true;
228  }
int dimension
Definition: GameState.hpp:22
int ** representation
Definition: GameState.hpp:21
Here is the caller graph for this function:

◆ setRepresentation()

void GameState::setRepresentation ( int **  representation)
inline

Definition at line 328 of file GameState.hpp.

328  {
330 
331  //dimension must be recalculated
332  dimension = sizeof(representation[0]) / sizeof(representation[0][0]) + 1;
333  }
int dimension
Definition: GameState.hpp:22
int ** representation
Definition: GameState.hpp:21
Here is the caller graph for this function:

◆ to_line_string()

string GameState::to_line_string ( ) const
inline

Returns a single line string representation of the 8-puzzle board state.

Returns
single line string representation of the state

Definition at line 304 of file GameState.hpp.

304  {
305  string tmp = "";
306 
307  for (int x = 0; x < dimension; x ++) {
308  for (int y = 0; y < dimension; y ++) {
309  tmp.append(std::to_string(representation[x][y])).append(" ");
310  }
311  }
312  return tmp.erase(tmp.find_last_not_of(" \n\r\t") + 1);
313  }
int dimension
Definition: GameState.hpp:22
int ** representation
Definition: GameState.hpp:21

◆ to_string()

string GameState::to_string ( ) const
inline

Returns a multi-line string representation of the 8-puzzle board state.

Returns
multi-line string representation of the state

Definition at line 290 of file GameState.hpp.

290  {
291  string tmp = "";
292 
293  for (int x = 0; x < dimension; x ++) {
294  for (int y = 0; y < dimension; y ++) {
295  tmp.append(std::to_string(representation[x][y])).append(" ");
296  }
297  tmp.append("\n");
298  }
299  return tmp;
300  }
int dimension
Definition: GameState.hpp:22
int ** representation
Definition: GameState.hpp:21

◆ toIntArray()

int* GameState::toIntArray ( string  s)
inlineprivate

Turns a string representation of an 8-puzzle into an array.

Parameters
sstring representation of an 8-puzzle
Returns
Pointer to an int array containing the state of the puzzle

Definition at line 28 of file GameState.hpp.

28  {
29 
30  //count spaces in string
31  int spaces = 1;
32  for (int i = 0; i < s.length(); i ++) {
33  if (s[i] == ' ') spaces ++;
34  }
35 
36  //create array
37  int *ret = new int[spaces];
38 
39  int currentInt = 0;
40  string intString = "";
41  for (int i = 0; i < s.length(); i ++) {
42 
43  //glues it number together until a space is found
44  if (s[i] != ' ') {
45  intString += s[i];
46  }
47 
48  //space means end of number, turn it into an int and put it in the return array
49  if ((s[i] == ' ') || (i == s.length() - 1)) {
50  ret[currentInt ++] = stoi(intString);
51  intString = "";
52  }
53  }
54  return ret;
55  }

Field Documentation

◆ depth

int GameState::depth
private

Definition at line 22 of file GameState.hpp.

◆ dimension

int GameState::dimension
private

Definition at line 22 of file GameState.hpp.

◆ parent

GameState* GameState::parent
private

Definition at line 23 of file GameState.hpp.

◆ representation

int** GameState::representation
private

Definition at line 21 of file GameState.hpp.


The documentation for this class was generated from the following file: