同一个世界游戏 算法破解

1.游戏编码保存方式

将游戏用二维数组保存,例如下图保存为
终止状态

{0, 1, 1, 1, 1, 0},
{1, -1, -1, -1, -1, 1},
{1, 0, -1, -1, 0, 1},
{1, 0, -1, -1, 0, 1},
{1, 0, -1, -1, 0, 1},
{1, -1, 1, 1, -1, 1},
{0, 1, 1, 1, 1, 0}

或者

{0, -1, -1, -1, -1, 0},
{-1, 1, 1, 1, 1, -1},
{-1, 0, 1, 1, 0, -1},
{-1, 0, 1, 1, 0, -1},
{-1, 0, 1, 1, 0, -1},
{-1, 1, -1, -1, 1, -1},
{0, -1, -1, -1, -1, 0}

起点保存为

{5, 0},
{5, 5}

2.破解思路

游戏初始状态如下图,对应的二进制,换行方便观查

000000
000000
000000
000000
000000
000000
000000

初始状态
终止状态

000000
011110
001100
001100
001100
010010
000000

终止状态
中间状态

000000                  000000
111001                   100111
101001                  100101
101001                  100101
101001                  100101
101111                   111101
000000                  000000

中间状态-1 中间状态-2

000000 011110 001100 001100 001100 010010 000000 ^
000000 111001 101001 101001 101001 101111 000000 ^
000000 100111 100101 100101 100101 111101 000000 =
000000 000000 000000 000000 000000 000000 000000

实际上对应的二进制权重是

{
0, 1, 2, 3, 4, 5,
6, 7, 8, 9, 10, 11,
12, 13, 14, 15, 16, 17,
18, 19, 20, 21, 22, 23,
24, 25, 26, 27, 28, 29,
30, 31, 32, 33, 34, 35,
36, 37, 38, 39, 40, 41
}

跟上面的二进制数的权重是逆序关系

经过该点取该点的2^N+父节点的值,每经过一点都保存,所有路径都保存,对每条路径每一个点都进行检查

	// 检查是否是符合目标的路径
	private Node[] checkPass(Node parent) {
   
		long nextTarget = target;
		Node node = parent;
		Node[] nodes = new Node[startPoint.length];
		for (int i = 0; i < startPoint.length && node != null; i++) {
   
			nextTarget = nextTarget ^ node.getValue();
			nodes[i] = node;
			if (nextTarget == 0) {
   
				return nodes;
			} else if (nextTarget > 0) {
   
				node = path.get((node.getIndex() + 1) % path.size()).get(nextTarget);
			} else {
   
				break;
			}
		}
		return null;
	}

每个起点生成的路径放在不同Map里面,node = path.get((node.getIndex() + 1) % path.size()).get(nextTarget);这里交替查询起点路径

3.代码

Node.java

import java.util.HashMap;
import java.util.Map;

public class Node {
   

	private Long value; // 当前路径值
	private Node parent; // 父节点
	private Map<Integer, Integer> parentIndexs; // 所有父节点的数组索引(对应一维数组)
	private int row; // 当前节点的行
	private int col; // 当前节点的列
	private int index; // 起点序号
	
	public Node() {
   
		parentIndexs = new HashMap<>();
	}
	
	public Long getValue() {
   
		return value;
	}
	public void setValue(Long value) {
   
		this.value = value;
	}
	public Node getParent() {
   
		return parent;
	}
	public void setParent(Node parent) {
   
		this.parent = parent;
	}
	public Map<Integer, Integer> getParentIndexs() {
   
		return parentIndexs;
	}
	public void setParentIndexs(Map<Integer, Integer> parentIndexs) {
   
		this.parentIndexs = parentIndexs;
	}
	public int getRow() {
   
		return row;
	}
	public void setRow(int row) {
   
		this.row = row;
	}
	public int getCol() {
   
		return col;
	}
	public void setCol(int col) {
   
		this.col = col;
	}

	public int getIndex() {
   
		return index;
	}

	public void setIndex(int index) {
   
		this.index = index;
	}
}

NodeTree.java

import java.util.ArrayList;
import java.util.HashMap;
import java.util.LinkedList;
import java.util.List;
import java.util.Map;
import java.util.Queue;
import java.util.Stack;

public class NodeTree {
   

	private int[][] state; // 盘面
	private int row, col; // 二维数组行、列
	private long target; // 目标状态值
	private int [][] startPoint; // 起始点
	private List<Map<Long, Node>> path;
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值