我目前正在尝试编写一个能够使用反向跟踪找到游戏挂钩纸牌解决方案的程序。
我的程序接收包含起始板的txt文件。除了包含实际后跟踪部分的solve()函数之外,一切都已完成,这在概念上证明对我来说真的很难。我已经在一张纸上工作了一段时间,但我认为我没有取得多大进展。任何帮助将不胜感激。下面的示例txt文件,*
= peg,.
=未结头寸,2
=行3
=列
2 3
.**
**.
头文件
#pragma once
#include <string>
#include <fstream>
#include <iostream>
#include <sstream>
#include <exception>
using namespace std;
typedef unsigned char PegType;
class PegBoard
{
private:
int numRows;
int numCols;
char ** pegBoard;
enum Direction{UP,DOWN,LEFT,RIGHT};
PegType peg;
PegType EMPTY;
PegType openPosition;
public:
//constructor
PegBoard(istream &input);
//deconstructor
~PegBoard();
//toString
void toString() ;
//solve
bool solve(int x, int y);
private:
//isSolved
bool isSolved();
//canJump
bool canJump(int frmRow, int frmCol, Direction whichWay);
//jump
void jump(int frmRow, int frmCol, Direction whichWay);
//unjump
void unjump(int frmRow, int frmCol, Direction whichWay);
};
实施档案
#include "PegBoard.h"
//constructor
PegBoard::PegBoard(istream &input){
string dummyLine;
numCols = 0;
numRows = 0;
peg = '*';
EMPTY = ' ';
openPosition = '.';
//get rows and cols
getline(input,dummyLine);
numRows = dummyLine[0] - '0';
numCols = dummyLine[2] - '0';
pegBoard = new char* [numRows];
//generate starting board from txt file
while(!input.eof()){
for(int r=0; r<numRows; r++){
getline(input,dummyLine);
pegBoard[r] = new char[numCols];
for(int c=0; c<numCols; c++){
if(dummyLine[c] == peg || dummyLine[c] == EMPTY || dummyLine[c] == openPosition)
pegBoard[r][c] = dummyLine[c];
else
throw out_of_range("Invalid Board Configuration");
}//end [r][c]
}// end [r]
}// end file
}//end constructor
//deconstructor
PegBoard::~PegBoard(){
for (int i=0; i < numRows; i++)
delete [] pegBoard[i];
delete [] pegBoard;
}//end deconstructor
//solve function the one I still need to complete
bool PegBoard::solve(int x, int y){
//base case
if(isSolved())
return true;
else{
//attempt a jump at every direction
for(int i=0; i < 4; i++){
switch (i){
case 0: jump(x,y,UP);
break;
case 1: jump(x,y,DOWN);
break;
case 2: jump(x,y,LEFT);
break;
case 3: jump(x,y,RIGHT);
break;
default:
break;
}//end switch
}//end for
}//end else
solve(x+1,y);
return false;
}//end solve()
//isSolved
bool PegBoard::isSolved(){
int counter =0;
//travser through board and check to see if only one * remains.
for(int r=0; r<numRows; r++){
for(int c=0; c<numCols; c++){
if(pegBoard[r][c] == '*'){
counter ++;
}//end check
}//end [r][c]
}//end [r]
if(counter == 1)
return true;
else
return false;
}//end isSolved()
//canJump
bool PegBoard::canJump(int frmRow, int frmCol, Direction whichWay){
//check inputed values are in bounds
if(frmRow >= 0 && frmRow < numRows && frmCol >= 0 && frmCol < numCols){
//check if inputed values contains a *
if(pegBoard[frmRow][frmCol] == peg){
switch (whichWay)
{
case PegBoard::UP:
//check upward bounds
if(frmRow-2 >= 0){
//check if next to peg and if avaiable position to jump to
if(pegBoard[frmRow-1][frmCol] == peg && pegBoard[frmRow-2][frmCol] == openPosition)
return true;
}
break;
case PegBoard::DOWN:
//check downward bounds
if(frmRow+2 < numRows){
//check if next to peg and 2 spaces from open position
if(pegBoard[frmRow+1][frmCol] == peg && pegBoard[frmRow+2][frmCol] == openPosition)
return true;
}
break;
case PegBoard::LEFT:
//check left bounds
if(frmCol-2 >=0){
//check if next to peg and 2 spaces from open position
if(pegBoard[frmRow][frmCol-1] == peg && pegBoard[frmRow][frmCol-2] == openPosition)
return true;
}
break;
case PegBoard::RIGHT:
if(frmCol+2 < numCols){
//check if next to peg and 2 spaces from open position
if(pegBoard[frmRow][frmCol+1] == peg && pegBoard[frmRow][frmCol+2] == openPosition)
return true;
}
break;
default: return false;
break;
}//end switch
}//end peg check
}//end starting bounds check
return false;
}//end canJump
//jump
void PegBoard::jump(int frmRow, int frmCol, Direction whichWay){
/*
* **.
* ..*
*/
if(canJump(frmRow,frmCol,whichWay)){
switch (whichWay)
{
case UP:
// assign new position
pegBoard[frmRow-2][frmCol] = peg;
//delete starting position
pegBoard[frmRow][frmCol] = openPosition;
//delete jumped position
pegBoard[frmRow-1][frmCol] = openPosition;
break;
case DOWN:
// assign new position
pegBoard[frmRow+2][frmCol] = peg;
//delete starting position
pegBoard[frmRow][frmCol] = openPosition;
//delete jumped position
pegBoard[frmRow+1][frmCol] = openPosition;
break;
case LEFT:
// assign new position
pegBoard[frmRow][frmCol-2] = peg;
//delete starting position
pegBoard[frmRow][frmCol] = openPosition;
//delete jumped position
pegBoard[frmRow][frmCol-1] = openPosition;
break;
case RIGHT:
// assign new position
pegBoard[frmRow][frmCol+2] = peg;
//delete starting position
pegBoard[frmRow][frmCol] = openPosition;
//delete jumped position
pegBoard[frmRow][frmCol+1] = openPosition;
break;
default:
break;
}//end switch
}//end canJump
}//end jump
//unjump
void PegBoard::unjump(int frmRow, int frmCol, Direction whichWay){
//still need to do
switch (whichWay)
{
case UP:
// assign new position
pegBoard[frmRow-2][frmCol] = openPosition;
//delete starting position
pegBoard[frmRow][frmCol] = peg;
//delete jumped position
pegBoard[frmRow-1][frmCol] = peg;
break;
case DOWN:
// assign new position
pegBoard[frmRow+2][frmCol] = openPosition;
//delete starting position
pegBoard[frmRow][frmCol] = peg;
//delete jumped position
pegBoard[frmRow+1][frmCol] = peg;
break;
case LEFT:
// assign new position
pegBoard[frmRow][frmCol-2] = openPosition;
//delete starting position
pegBoard[frmRow][frmCol] = peg;
//delete jumped position
pegBoard[frmRow][frmCol-1] = peg;
break;
case RIGHT:
// assign new position
pegBoard[frmRow][frmCol+2] = openPosition;
//delete starting position
pegBoard[frmRow][frmCol] = peg;
//delete jumped position
pegBoard[frmRow][frmCol+1] = peg;
break;
default:
break;
}//end switch
}
答案 0 :(得分:4)
出于某种原因,您的solve
仅按特定顺序尝试单元格。
solve
最好具有以下结构(更高级别的伪代码):
check if we already won
for all x:
for all y:
for all directions dir:
if jump from (x, y) in direction dir is possible:
(1) do that jump
(2) recursively call solve
(3) undo that jump
到目前为止,你所缺少的是for all x: for all y:
部分和跳跃撤消。