- UID
- 72137
注册时间2011-2-7
阅读权限10
最后登录1970-1-1
周游历练
该用户从未签到
|
随机生成一个迷宫,一般这种问题要用并查集的,但是具体算法我没有上网查找过,所以自己想了一个,但是我的想法还不成熟,存在很多缺陷,望大牛们指正。
算法的思想是:
while( 入口和出口 不通)
{
....随机找个点 -> (x,y)
....随机找个方向->上/下/左/右 -> dx,dy = {0,1,-1}
....如果(x,y)和( x + dx , y + dy)有一个是墙
.........把墙去掉
.........联通(x,y) 和 (x+dx,y+dy)
}
如果 RP是负无穷的话,可能要搜很长时间。。。。
- /*
- * Auther:Knuth学徒
- * Lang:C++
- * Date:2011-2-12
- */
- #include<cstdio>
- #include<cstring>
- #include<cstdlib>
- #include<ctime>
- #include<iOStream>
- using namespace std;
- const int M = 5;
- const int N = 5;
- const int direction[4][2] = {(0,-1),(0,1),(-1,0),(1,0)};
- int father[M*N + 1]; //并查集的父节点记录数组
- int map[N][M]; //地图数组
- /////////////////////////////////////////////////
- // 函数名:hash
- // 参数:横坐标和纵坐标以及棋盘的列大小
- // 前提:None
- // 返回:坐标的散列值
- /////////////////////////////////////////////////
- int hash(int x,int y, int col)
- {
- return ( x * col + y );
- }
- /////////////////////////////////////////////////
- // 函数名:id
- // 参数:点的散列值,存在a和b中
- // 前提:None
- // 返回:引用传值回去
- /////////////////////////////////////////////////
- void id(int val, int &a,int &b)
- {
- a = val/M;
- b = val%M;
- }
- /////////////////////////////////////////////////
- // 函数名:Make
- // 参数:None
- // 前提:None
- // 返回:None
- // 描述:并查集的初始化过程
- /////////////////////////////////////////////////
- void Make()
- {
- for(int i=0;i<N;++i)
- for(int j = 0;j<M;++j)
- {
- father[hash(i,j,M)] = hash(i,j,M);
- // printf("f[%d] = %d ",hash(i,j,M),father[hash(i,j,M)]);
- }
- }
- /////////////////////////////////////////////////
- // 函数名:FindSet
- // 参数:节点X表示某个点的散列值
- // 前提:None
- // 返回:节点x的祖先
- // 描述:递归时采用了路径压缩
- /////////////////////////////////////////////////
- int FindSet(int x)
- {
- if( x != father[x])
- {
- father[x] = FindSet(x);
- }
- return father[x];
- }
- /////////////////////////////////////////////////
- // 函数名:Union
- // 参数:两个散列值
- // 前提:None
- // 返回:None
- // 描述:合并两个集合
- /////////////////////////////////////////////////
- void Union(int a,int b)
- {
- father[a] = b;
- }
- int main()
- {
- Make();
- int sx,sy,ex,ey;
- srand((unsigned)time(0));
- int a = rand() % M*N; //入口
- int b = rand() % M*N; //出口
- id(a,sx,sy);
- id(b,ex,ey);
- map[sx][sy] = map[ex][ey] = 0;
- // cout<<"a = "<<a<<endl;
- // cout<<"b = "<<b<<endl;
- // cout<<"f[a]="<<father[a]<<endl;
- //cout<<"f b="<<father[b]<<endl;
- while(FindSet(a) != FindSet(b))
- //如果入口和出口不联通
- {
- int tmp = rand() % M*N;
- //随机选一点
- int dire = rand()%4;
- int tx,ty,ttx,tty;
- id(tmp,tx,ty);
- // printf("%d %d",tx,ty);
- ttx = tx + direction[dire][0];
- tty = ty + direction[dire][1];
- if(map[tx][ty] || map[ttx][tty])
- {
- map[tx][ty] = (map[tx][ty] == 1 ? 0:0);
- map[ttx][tty] = (map[ttx][tty] == 1 ? 0:0);
- Union(hash(tx,ty,M),hash(ttx,tty,M));
- }
- }
- // cout<<"OK2"<<endl;
- for(int m = 0;m<N;++m)
- {
- for(int n =0;n<M;++n)
- {
- printf("%d",map[m][n]);
- }
- printf("\n");
- }
- return 0;
- }
复制代码 |
|