转珠游戏-三消游戏-智龙迷城-神魔之塔-转珠算法的实现(一)-combo计算

转珠游戏算法1-combo计算转珠游戏介绍智龙迷城最短路径?消珠问题简化算法实现CODE (C++)结论转珠游戏介绍转珠游戏不同于传统三消游戏,传统三消是通过单次移动(移位)消除相连的珠子(以下简称COMBO).转珠游戏是通过移动珠子(可以理解单次操作多次移位)。在形成最终版面后一并计算结果,本系列主要探索消珠算法,最短路径算法,最优路径解等。智龙迷城这边用转珠游戏代表作,日本itunes app常年前三的国民游戏,智龙迷城为例通过移动红色珠子 如箭头移动后,可以达到两次消除(combo)(可以
摘要由CSDN通过智能技术生成

转珠游戏介绍

转珠游戏不同于传统三消游戏,传统三消是通过单次移动(移位)消除相连的珠子(以下简称COMBO).转珠游戏是通过移动珠子(可以理解单次操作多次移位)。在形成最终版面后一并计算结果,本系列主要探索消珠算法,最短路径算法,最优路径解等。

智龙迷城

这边用转珠游戏代表作,日本itunes app常年前三的国民游戏,智龙迷城为例
智龙迷城
通过移动红色珠子 如箭头移动后,可以达到两次消除(combo)(可以脑里模拟一下)

最短路径?

这类游戏的算法已经非常成熟,基本是通过dfs或者djstra、抑或是floyd去求解的,(官方也有自动路径,但是只有三步,推测暴力算的)
市面上的APP用过几个都是无法求到最优解(版面最大COMBO),怀疑也是floyd或者暴力+剪枝(这一部分不确定,如果我错了先说声抱歉)
在求最短路径算法之前,我们需要一个模拟获取游戏结果的算法:

消珠问题简化

转珠游戏分两种,一种是通过移动一个珠子N次,另一种是移动”任意”珠子“N次(业界俗称CTW:即Change the world)达到版面最大COMBO

即:在N x M的二维数组中,任意交换两个相邻元素,N次交换后达到最大Combo(CTW),如果限定除开始位置外,每次移动均限制为上一次移动的对象,即转为本次问题,如下所示:
1 2 6 2 2 2
5 6 4 4 1 3
1 6 4 1 3 1
1 6 4 2 2 1
1 5 5 3 3 1
上述数组进行消珠后,返回7,并且数组变为

--------------next combo---------
0 0 0 0 0 0
0 0 0 0 0 0
0 0 0 4 0 0
0 0 0 1 1 0
1 2 6 2 2 0
注:
1.移动包括上下左右,不包括斜角,因为斜角移动可以通过:左右→上下,两次移动达到同样效果,这样可以简化问题。
2.消除条件为,同一直线(不包括斜角)有相同属性的元素>=n(n为消珠限制且默认为3),则进行消除,全部消除完毕后,剩余珠子会掉落下来,掉落的珠子如果形成消除的话会再进行消除。

算法实现

对于元素分组问题一般是用并查集或者dfs实现,因为本问题行列均不大于10,使用DFS即可。

然而本文用的bfs
大概的伪代码如下:

int 获取最大combo(matrix[][]):
for each col row:{
bfs队列.push(最后一个非0元素).
标记该位置已被访问
while(bfs不为空) {
向四个方向寻找元素相同解
if(存在相同解)则bfs.push,且标记该位置已被访问 } }
int result = 执行combo计算(标记数组[][])
执行消除(matrix[][])
执行模拟掉落(matrix[][])
执行递归(this.获取最大combo(matrix[][]))

CODE (C++)

// 点集合 包含是否存在加珠,珠子类型等
struct binary
{
   
    //珠类型
    int cata;
    //是否存在combo增加
    bool comboPlus = false;
    int i,j;
    binary(int x ,int i,int j) : cata(x), i(i), j(j){
   }
};
//单论消珠完成后进行掉落,每次迭代返回掉落后的数组
void finish(vector<vector<int>> &matrix)
{
   
    int sizeCol = matrix.size(), sizeRow = matrix[0].size();
    for (int i = sizeCol - 1; i >= 0; --i)
        for (int j = sizeRow - 1; j >= 0; --j)
        if(matrix[i][j]==0){
   
            int ii=i-1;
            while(ii>=0){
   
                if(matrix[ii][j]>0) {
   
                    matrix[i][j] = matrix[ii][j];
                    matrix[ii][j] = 0;
                    break;
                }
                ii--;
            }
        }
    cout<<endl;
    cout<<
  • 1
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值