锯齿数独 cocos2d-x 开发 (二)
来源:互联网 发布:荼靡 知乎 编辑:程序博客网 时间:2024/05/16 08:36
锯齿数独 cocos2d-x 开发 (一)
二、锯齿的生成
1、9*9的格子划分成9个随机形状的连通块。
这里采用了bfs + 并查集的算法。 在bfs生成连通块的同时,检测整个图所有的联通分量, 一些特殊的情况进行剪枝。
bfs 函数如下:
bool JigsawHelper:: bfs(int i, int j, int groupId){ bool vis[81]; memset(vis, 0, sizeof(vis)); int n = i * 9 + j; vis[n] = true; queue<int>q; q.push(n); add(i,j,q,vis); int cnt = 1;// cout<<"-------------------"<<endl; while (cnt <= 9 && !q.empty()) { int tp = q.front(); q.pop(); g[tp] = groupId; if (!check(n)) { g[tp] = 0; continue; } cnt ++; add(tp/9,tp%9,q,vis);// cout<<"("<<tp/9<<","<<tp%9<<")"; }// cout<<"-------------------"<<endl; if (cnt < 10) { // cout<<"cnt: "<<cnt<<endl; return false; } return true;}
check()用于检测当前情况下能否有机会成功划分。
这里有两个重要的判定:
1) 生成过程中不同连通块的个数不得超过九个。
2)生成一个连通块完毕后,剩下的连通块中不能有个数不为9的倍数。
int cnt[81]; memset(cnt,0,sizeof(cnt)); for (int i = 0; i < 81; i++) { int num = FindSet(i); cnt[num]++; } int nParent = FindSet(n); int ans = 0; int small = 0; for (int i = 0; i < 81; i++) { if (cnt[i] == 0) continue; if (cnt[i]%9 != 0) //连通个数不是9的倍数 { ans ++; } if (cnt[i]%9 != 0 && i != nParent) //小于9的连通块 { small += cnt[i]%9; } } if (cnt[nParent] != 9) //生成过程中小连通块的个数和当前块的和大于9 { if (small + cnt[nParent] > 9) return false; } if (cnt[nParent] == 9 && ans > 0) //生成结束后仍然有个数不为9的倍数的连通块 return false; return true;
到这里并没有结束,仍然有一些刁钻的数据会造成无法继续往下生成的情况,好在只有20%左右的几率。
项目不是做题,复杂度不大,rebuild即可。
void JigsawHelper:: build(){ srand(time(NULL)); memset(g,0,sizeof(g)); vector<int>vt; for (int i = 0; i < 81; i++) vt.push_back(i); for (int groupId = 1; groupId <= 9; groupId++) { int num = vt[rand()%vt.size()]; if (!bfs(num/9, num%9, groupId)) { cout<<"fail!!!!!!!!!!! rebuild"<<endl; build(); return; } vt.clear(); for (int i = 0; i < 81; i++) { if (g[i] == 0) vt.push_back(i); } } checkColor();}
2、 染色
由于四色定理的存在,预先准备四种不同的颜色。
将每个连通块看做一个节点,Welch Powel法染色即可。
3、数独的生成及tricks。
获取锯齿数组和颜色数组后就可以重新用DLX解精确覆盖问题了,构造的时候方式略不同而已。
但是最终生成的时候却偶尔会出现卡死的情况!
对于一种锯齿并不是确定有解的。所以这里修改了下生成数独的方式并添加了一些剪枝。
1)选取种子的时候只取一个随机格子随机数。
2)dlx 中dfs时超过一定deep就return false。多次测试取15000。
3)算不出结果继续rebuild, 相信cpu的实力。(实测ipad mini2以上 生成所有难度均在1s之内,完全可以接受的范围)。
4、UI
我只是在简单的背景上添加了81个不同颜色的editbox,限制一下整数。
当然有时间换成用button选择肯定是更好的
void SudokuUI::editBoxTextChanged(EditBox *editBox, const std::string &text){ char buffer[2]; if (text.length() >= 1) { char c = text[text.length() - 1]; if (!isdigit(c)) { editBox->setText(""); return; } sprintf(buffer, "%c",c); editBox->setText(buffer); }}
由于锯齿形本身限制较多, 所以比较容易挖更多的洞,生成的效果也明显好一些,感受下难度吧XD~
- 锯齿数独 cocos2d-x 开发 (二)
- 锯齿数独 cocos2d-x 开发 (一)
- Cocos2d-x 反锯齿
- cocos2d-x游戏开发实例(二)
- Cocos2d-X游戏开发(二)
- 数独游戏开发
- Android开发-自定义View-AndroidStudio(二十四)数独(1)
- 【Cocos2d-x游戏引擎开发笔记(19)】简单数据存储以及抗锯齿
- 【Cocos2d-x游戏引擎开发笔记(19)】简单数据存储以及抗锯齿
- cocos2d-x游戏开发回调函数
- cocos2d-x游戏开发 回调函数
- cocos2d-x游戏开发回调函数
- cocos2d-x游戏开发 回调函数
- cocos2d-x游戏开发回调函数
- Cocos2d-x 3.0开发(二)使用自动脚本创建cocos2d-x 3.0项目
- Cocos2d-x 3.0开发(二)使用自动脚本创建cocos2d-x 3.0项目
- Cocos2d-x 3.0开发(二)使用自动脚本创建cocos2d-x 3.0项目
- Cocos2d-x 3.0开发(二)使用自动脚本创建cocos2d-x 3.0项目
- java151227ExceptionDemo2
- Spark 1.6.0 (Scala 2.11)版本的编译与安装部署
- the 4th national media processing meeting
- 商业英语句型09
- this,this,再次讨论javascript中的this,超全面
- 锯齿数独 cocos2d-x 开发 (二)
- POJ-1975 Median Weight Bead(Floyed)
- Android 使用Parcelable传递对象
- 盘点即时战略游戏中高实用性寻路算法
- java151229ExceptionTest
- 2016-01-06 09:42:53.547:WARN:oejs.HttpChannel:qtp2109938810-27: Could not send response error 500: j
- ES6学习——新的语法:Symbols——Symbol.toPrimitive,Symbol.hasInstance,Symbol.toStringTag,Symbol.species
- MFC中Unicode与多字节编码中遇到的CString与char或char*的转化问题
- Spring+Hibernate声明事务