import java.util.Arrays;
public class Test {public static final int LEFT_UP = 0;//左上
public static final int UP_LEFT = 1;//上左
public static final int UP_RIGHT = 2;//上右
public static final int RIGHT_UP = 3;//右上
public static final int RIGHT_DOWN = 4;//右下
public static final int DOWN_RIGHT = 5;//下右
public static final int DOWN_LEFT = 6;//下左
public static final int LEFT_DOWN = 7;//左下
public static int currentNum = 1;//马的步数本来就位1,因为出生地算一个
public static int goalNum = 8;//寻找的目标数,如果goalNum为4,则目标数为16
public static void main(String[] args) {long start = System.currentTimeMillis();
for (int x = 0; x< goalNum; x++) {for (int y = 0; y< goalNum; y++) {int[] position = {x, y};//马儿的初始位置
int[][] map = new int[goalNum][goalNum];//地图
map[position[0]][position[1]] = 1;
for (int direction = LEFT_UP; direction<= LEFT_DOWN; direction++) {if (move(direction, position, map)) {//如果递归成功
long end = System.currentTimeMillis();
System.out.println(String.format("总耗时为%d秒", (end - start) / 1000));
return;
}
}
}
}
}
public static boolean judgePosition(int[] position, int[][] map) {//判断路况是否合法即每走完一步,落脚点必须在棋盘内,期盼的边界为 [0,0]-[3,3],且棋盘当前位置不能重新踩
return ((position[0] >= 0 && position[0]<= goalNum - 1) && (position[1] >= 0 && position[1]<= goalNum - 1)) && map[position[0]][position[1]] != 1;
}
//递归一次,currentNum就得+1
public static boolean move(int direction, int[] position, int[][] map) {//移动
if (currentNum == goalNum * goalNum) {//如果当前数量已经达到了递归的目标数,则返回true
printMap(position, map);
return true;
} else {currentNum++;//当前数量+1
int[] positionCopy = Arrays.copyOf(position, position.length);//一进入这个方法,就将position的值保存下来
int[][] mapCopy = new int[goalNum][goalNum];
for (int i = 0; i< goalNum; i++) {for (int j = 0; j< goalNum; j++) {mapCopy[i][j] = map[i][j];
}
}
modifyPosition(direction, position);//修改位置
if (!judgePosition(position, map)) {//如果修改的坐标不合法或者说原有地图此位置已经为1
currentNum--;//当前数量-1
restorePosition(direction, position);//将坐标进行还原
return false;
}
map[position[0]][position[1]] = 1;
贪心算法,执行速度为0秒//
int[] sortedDirections = getSortedDirections(position);//经过排序的方向数组
for (int nextDirection : sortedDirections) {if (move(nextDirection, position, map)) {//如果递归成功
printMap(positionCopy, mapCopy);
return true;
}
}
//无贪心算法/
// for (int nextDirection = LEFT_UP; nextDirection<= LEFT_DOWN; nextDirection++) {//没贪心算法
// if (move(nextDirection, position, map)) {//如果递归成功
// printMap(positionCopy, mapCopy);
// return true;
// }
// }
map[position[0]][position[1]] = 0;
restorePosition(direction, position);//将坐标进行还原
currentNum--;//当前数量-1
return false;
}
}
public static int[] getSortedDirections(int[] position) {//将原先代码执行速度从10分钟提升到0秒的关键所在
int[] directions = {LEFT_UP, UP_LEFT, UP_RIGHT, RIGHT_UP, RIGHT_DOWN, DOWN_RIGHT, DOWN_LEFT, LEFT_DOWN};//八个方向
for (int i = 0; i< directions.length; i++) {int min = i;//假设当前这个方向是离边界最短距离
for (int j = i; j< directions.length; j++) {int[] position1 = {position[0], position[1]};
int positionDistance = 0;
modifyPosition(directions[j], position1);
if (position1[0] >3) {positionDistance += goalNum - 1 - position1[0];
} else {positionDistance += position1[0];
}
if (position1[1] >3) {positionDistance += goalNum - 1 - position1[1];
} else {positionDistance += position1[1];
}
int[] position2 = {position[0], position[1]};
int minPositionDistance = 0;
modifyPosition(directions[min], position2);
if (position2[0] >3) {minPositionDistance += goalNum - 1 - position2[0];
} else {minPositionDistance += position2[0];
}
if (position2[1] >3) {minPositionDistance += goalNum - 1 - position2[1];
} else {minPositionDistance += position2[1];
}
if (positionDistance< minPositionDistance) {min = j;
}
}
int temp = directions[i];
directions[i] = directions[min];
directions[min] = temp;
}
return directions;
}
public static void modifyPosition(int direction, int[] position) {//修改位置
switch (direction) {case LEFT_UP:
position[0] -= 1;
position[1] -= 2;
break;
case UP_LEFT:
position[0] -= 2;
position[1] -= 1;
break;
case UP_RIGHT:
position[0] -= 2;
position[1] += 1;
break;
case RIGHT_UP:
position[0] -= 1;
position[1] += 2;
break;
case RIGHT_DOWN:
position[0] += 1;
position[1] += 2;
break;
case DOWN_RIGHT:
position[0] += 2;
position[1] += 1;
break;
case DOWN_LEFT:
position[0] += 2;
position[1] -= 1;
break;
case LEFT_DOWN:
position[0] += 1;
position[1] -= 2;
break;
}
}
public static void restorePosition(int direction, int[] position) {//还原位置
switch (direction) {case LEFT_UP:
position[0] += 1;
position[1] += 2;
break;
case UP_LEFT:
position[0] += 2;
position[1] += 1;
break;
case UP_RIGHT:
position[0] += 2;
position[1] -= 1;
break;
case RIGHT_UP:
position[0] += 1;
position[1] -= 2;
break;
case RIGHT_DOWN:
position[0] -= 1;
position[1] -= 2;
break;
case DOWN_RIGHT:
position[0] -= 2;
position[1] -= 1;
break;
case DOWN_LEFT:
position[0] -= 2;
position[1] += 1;
break;
case LEFT_DOWN:
position[0] -= 1;
position[1] += 2;
break;
}
}
public static void printMap(int[] position, int[][] map) {for (int i = 0; i< goalNum; i++) {for (int j = 0; j< goalNum; j++) {System.out.print(map[i][j] + " ");
}
System.out.println();
}
System.out.println(Arrays.toString(position));
System.out.println("=======================");
}
}
你是否还在寻找稳定的海外服务器提供商?创新互联www.cdcxhl.cn海外机房具备T级流量清洗系统配攻击溯源,准确流量调度确保服务器高可用性,企业级服务器适合批量采购,新人活动首月15元起,快前往官网查看详情吧
创新互联公司是一家集网站建设,古冶企业网站建设,古冶品牌网站建设,网站定制,古冶网站建设报价,网络营销,网络优化,古冶网站推广为一体的创新建站企业,帮助传统企业提升企业形象加强企业竞争力。可充分满足这一群体相比中小企业更为丰富、高端、多元的互联网需求。同时我们时刻保持专业、时尚、前沿,时刻以成就客户成长自我,坚持不断学习、思考、沉淀、净化自己,让我们为更多的企业打造出实用型网站。