因?yàn)榍皫滋烊フ搲吹接芯W(wǎng)友問(wèn)迷宮算法的問(wèn)題,所以抽空研究了一下搜索算法.我把很久以前寫(xiě)的
一個(gè)走迷宮的程序貼上去了.這個(gè)程序比較土,不會(huì)判斷隨機(jī)產(chǎn)生的迷宮是否能走通,不是按最短路徑搜索,但是,只要是能連通的迷宮就肯定能走出去.呵呵,很土的一個(gè)方法,自已瞎琢磨了.
以前的程序算法是這樣的:
1.隨機(jī)產(chǎn)生由0x00和0xff結(jié)成的地圖
2.從(0,0)點(diǎn)開(kāi)始進(jìn)入迷宮
3.因?yàn)槌隹谠?MAXX,MAXY),所以搜索方向是 右->下->上->左
4.每走過(guò)一個(gè)方格把此方格對(duì)應(yīng)的值加1
5.在選擇方向時(shí),總是優(yōu)先選擇方格值最小的相鄰方格,這樣,一個(gè)方格走過(guò)的次數(shù)越多就越不會(huì)再次走入, 所以自然而然就會(huì)走到(MAXX,MAXY)了
這種算法導(dǎo)致"小人"會(huì)在迷宮里不停的走來(lái)走去,很多時(shí)候是在重復(fù)走動(dòng),看起來(lái)傻傻的(俺喜歡)
為了解決判斷迷宮是否能走通問(wèn)題,和求最短路徑問(wèn)題,我想了很久.
網(wǎng)上有網(wǎng)友說(shuō)可以用A*算法來(lái)探路比較好,我去找了幾篇資料,沒(méi)看太懂,
自已瞎折騰一通,又搞出一個(gè)新算法,也不知道學(xué)名叫什么,反正結(jié)果看起來(lái)是對(duì)的.呵呵
新的算法是這樣的:
1.隨機(jī)產(chǎn)生由0x00和0xff結(jié)成的地圖
2.建立一個(gè)空的"連通地圖方格列表",然后用遞歸方法去搜索所有與(0,0)相同值的方格,然后把坐格存入"連通地圖方格列表"中 在遞歸時(shí),如果碰到"連通地圖方格列表"中已經(jīng)存在的方格則跳出.這樣,就產(chǎn)生了一個(gè)"連通地圖方格列表",然后只要 判斷迷宮入口坐標(biāo)(0,0)和出口坐標(biāo)(MAXX,MAXY)是否都在列表時(shí)就可以知道是否迷宮能走通了,好簡(jiǎn)單吧:)
3.把迷宮入口坐標(biāo)(0,0)的賦值為1,然后用雙重循環(huán)判斷迷宮中每一方格,如果一個(gè)方格的值>1且小于255的話(huà),則把相鄰 的方格值全部加1,如果某一個(gè)相鄰方格的值比所在方格值+1還要大的話(huà)(因?yàn)檫B通的原因),則把相鄰方格設(shè)成方格值+1 重復(fù)這樣做,直到 出口坐標(biāo)(MAXX,MAXY) 也被賦值為止.
4.現(xiàn)在工作就很簡(jiǎn)單了,從出口坐標(biāo)(MAXX,MAXY)開(kāi)始向上推,逐次遞減直到入口坐標(biāo)(0,0),這樣就得到了一個(gè)由多個(gè)坐標(biāo)組成的路線(xiàn)表,也就是最短路徑了(看起來(lái)是的)
5.因?yàn)槭窃诶系某绦蚧A(chǔ)上改的,也沒(méi)有仔細(xì)弄,把最短路徑經(jīng)過(guò)方格全部設(shè)為0,把其它連通的方格則全部設(shè)為1, 這樣老的程序不做什么修改就OK了.
6.欣賞了幾十遍小人走通迷宮的路線(xiàn),直是簡(jiǎn)潔,呵呵. 在解決迷宮問(wèn)題的同時(shí),俺發(fā)現(xiàn)判斷連通的原理和繪圖時(shí)填充算法其實(shí)是一回事,以后可以自已寫(xiě)填充函數(shù)了:)
迷宮問(wèn)題雖然是小問(wèn)題,但是擴(kuò)展開(kāi)來(lái)又可以解決別的問(wèn)題了,如地圖導(dǎo)航之類(lèi)的.
這個(gè)程序及源代碼的下載地址在:
- /*
- 這是一個(gè)研究最短迷宮尋路算法程序
-
- mail:szluosj@21cn.com
- */
- #include <stdio.h>
- #include <stdlib.h>
- #include <conio.h>
- #include <dos.h>
- #include <iostream.h>
- const int XSIZE = 60;
- const int YSIZE = 45;
- const int DIE = 255;
- unsigned long count=0;
- unsigned char Map[YSIZE][XSIZE];
- int g_SameAreaList[YSIZE*XSIZE][2]; //相同區(qū)域的列表
- int g_iSameAreaCount = 0;
- int g_ShortPathList[YSIZE*XSIZE][2]; //最段的路徑點(diǎn)列表
- int g_iShortPathCount = 0;
- int dir[4][2]=
- {
- 1 , 0,
- 0 , 1,
- 0 , -1,
- -1, 0
- };
- int xx=0,yy=0;
- int oldxx=xx,oldyy=yy;
- //枚舉一條線(xiàn)段上的所有點(diǎn)
- int LineDDA(int x1,int y1,int x2,int y2,void *p_pData)
- {
- int i,p,n,x,y,tn,j;
- int iIndex = 0;
- int *pData = (int *)p_pData;
-
- if( y1==y2 ) //是一橫線(xiàn)
- {
- if(x1>x2)
- {
- x=x2; x2=x1; x1=x;
- }
-
- for (j=x1;j<=x2;j++)
- {
- pData[iIndex] = j;
- pData[iIndex+1] = y1;
- iIndex+=2;
- }
- return iIndex;
- }
-
- if( x1==x2 ) //是一豎線(xiàn)
- {
- if(y1>y2)
- {
- y=y2; y2=y1; y1=y;
- }
-
- for (j=y1;j<=y2;j++)
- {
- pData[iIndex] = x1;
- pData[iIndex+1] = j;
- iIndex+=2;
- }
- return iIndex;
- }
-
- if( abs(y2-y1) <= abs(x2-x1) )
- {
- if( (y2<y1&&x2<x1) || (y1<=y2&&x1>x2) )
- {
- x=x2; y=y2; x2=x1; y2=y1; x1=x; y1=y;
- }
-
- if( y2>=y1 && x2>=x1 )
- {
- x=x2-x1;
- y=y2-y1;
- p=2*y;
- n=2*x-2*y;
- tn=x;
-
- while(x1<=x2)
- {
- if(tn>=0)
- tn-=p;
- else
- {
- tn+=n;
- y1++;
- }
-
- pData[iIndex] = x1;
- pData[iIndex+1] = y1;
- iIndex+=2;
-
- x1++;
- }
- }
- else
- {
- x=x2-x1;
- y=y2-y1;
- p=-2*y;
- n=2*x+2*y;
- tn=x;
- while(x1<=x2)
- {
- if(tn>=0)
- tn-=p;
- else
- {
- tn+=n;
- y1--;
- }
- pData[iIndex] = x1;
- pData[iIndex+1] = y1;
- iIndex+=2;
-
- // putpixel(x1,y1);
- x1++;
- }
- }
- }
- else
- {
- x=x1; x1=y2; y2=x; y=y1; y1=x2; x2=y;
- if( (y2<y1&&x2<x1) || (y1<=y2&&x1>x2) )
- {
- x=x2; y=y2; x2=x1; y2=y1; x1=x; y1=y;
- }
-
- if( y2>=y1 && x2>=x1 )
- {
- x=x2-x1; y=y2-y1;
- p=2*y; n=2*x-2*y; tn=x;
- while(x1<=x2)
- {
- if(tn>=0)
- tn-=p;
- else
- {
- tn+=n;
- y1++;
- }
- // putpixel(y1,x1);
- pData[iIndex] = y1;
- pData[iIndex+1] = x1;
- iIndex+=2;
-
- x1++;
- }
- }
- else
- {
- x=x2-x1; y=y2-y1;
- p=-2*y; n=2*x+2*y; tn=x;
-
- while(x1<=x2)
- {
- if(tn>=0)
- tn-=p;
- else
- {
- tn+=n;
- y1--;
- }
- // putpixel(y1,x1);
- pData[iIndex] = y1;
- pData[iIndex+1] = x1;
- iIndex+=2;
-
- x1++;
- }
- }
- }
- return iIndex;
- }
- void ShowXY()
- {
- textattr(0x0f);
- gotoxy(70,1);
- cprintf("X=%u",xx);
- gotoxy(70,2);
- cprintf("Y=%u",yy);
- gotoxy(65,4);
- cprintf("Total= %lu",count);
- }
- void ClearMap()
- {
- for (int y=0;y<YSIZE;y++)
- {
- for (int x=0;x<XSIZE;x++)
- {
- Map[y][x]=0;
- }
- }
- }
- void MakeMap()
- {
- int y,x;
- int iData;
-
- ClearMap();
- randomize();
- for (y=0;y<YSIZE;y++)
- {
- for (x=0;x<XSIZE;x++)
- {
- iData = random(1000);
- if ( (iData>0) && (iData<300) )
- Map[y][x]=DIE;
- }
- }
- for (y=0;y<5;y++)
- {
- for (x=0;x<5;x++)
- {
- Map[y][x]=0;
- Map[YSIZE-y-1][XSIZE-x-1]=0;
- }
- }
- }
- void DrawBox(int x1,int y1,int x2,int y2)
- {
- textattr(0x7);
- for (int i=0;i<x2-x1;i++)
- {
- gotoxy(i+x1,y1);
- cprintf("?);
- gotoxy(i+x1,y2);
- cprintf("?);
- }
- for (i=0;i<y2-y1;i++)
- {
- gotoxy(x1,y1+i);
- cprintf("?);
- gotoxy(x2,y1+i);
- cprintf("?);
- }
-
- }
- void ShowMan()
- {
- gotoxy(oldxx+2+1,oldyy+2+1);
- textattr(14);
- cprintf(".");
-
- gotoxy(xx+2+1,yy+2+1);
- textattr(13);
- cprintf("");
- }
- void ShowMap()
- {
- int X=2,Y=2;
- DrawBox(X,Y,X+XSIZE+1,Y+YSIZE+1);
- gotoxy(X+XSIZE+1,Y+YSIZE);
- cprintf(" ");
- gotoxy(X+1,Y);
- cprintf(" ");
-
- for (int y=0;y<YSIZE;y++)
- {
- for (int x=0;x<XSIZE;x++)
- {
- gotoxy(x+X+1,y+Y+1);
- switch(Map[y][x])
- {
- case DIE:
- textattr(4);
- cprintf("?);
- break;
- case 254:
- textattr(0x2);
- cprintf("?);
- case 0:
- case 1:
- textattr(0x0f);
- cprintf(" ");
- break;
- default:
- textattr(0x0E);
- cprintf(".");
- }
-
- }
- }
- }
- int isOver()
- { //判斷是否死路, 判斷是不是所有走過(guò)的路周?chē)紱](méi)有路了,如果是這樣就是死路了
- int y,x;
- //看看是不是還有氣
- for (y=0;y<YSIZE;y++)
- {
- for (x=0;x<XSIZE;x++)
- {
- if (Map[y][x]==0)
- continue;
-
- if (Map[y][x]==DIE)
- continue;
-
- if (y>1)
- if (Map[y-1][x]==0)
- return 0;
-
- if (y<YSIZE-1)
- if (Map[y+1][x]==0)
- return 0;
-
- if (x>1)
- if (Map[y][x-1]==0)
- return 0;
-
- if (x<XSIZE-1)
- if (Map[y][x+1]==0)
- return 0;
- }
- }
-
- return 1;
- }
- int GoToThere()
- {
- int tx,ty;
- unsigned char dd[4];
- int i,j,d;
- unsigned char min,data;
-
- for (d=0;d<4;d++)
- {
- tx = xx + dir[d][0];
- ty = yy + dir[d][1];
- if ((tx>=XSIZE)||(tx<0))
- {
- dd[d]=DIE;
- continue;
- }
- if ((ty>=YSIZE)||(ty<0))
- {
- dd[d]=DIE;
- continue;
- }
- dd[d]=Map[ty][tx];
- }
-
- data=dd[0];
- min=0;
-
- for (i=0;i<4;i++)
- {
- if (data>dd[i])
- {
- data=dd[i];
- min = i;
- }
- }
-
- return min;
- }
- int Go()
- {
- int i,d;
- count++;
- d = GoToThere();
- oldxx=xx;
- oldyy=yy;
- xx = xx + dir[d][0];
- yy = yy + dir[d][1];
- Map[oldyy][oldxx]++;
-
- if (Map[oldyy][oldxx]==1)
- Map[oldyy][oldxx] = 2;
-
- return 0;
- }
- int Success()
- {
- if ((xx>=XSIZE-1) && (yy>=YSIZE-1))
- {
- // do
- // {
- gotoxy(70,5);
- textattr(0xee);
- cprintf("SUCCESS!"); //SUCCESS!
- gotoxy(70,6);
- textattr(0xee);
- cprintf("Esc to Exit");
- // } while(getch()!=27);
- return 0;
- }
- return -1;
- }
- int isExistPosInSameAreaList(int p_iX,int p_iY)
- {
- for (int i=0;i<g_iSameAreaCount;i++)
- {
- if ( (g_SameAreaList[i][0] == p_iX) && (g_SameAreaList[i][1] == p_iY) )
- return 1;
- }
-
- return 0;
- }
- int AddOnePosToSameAreaList(int p_iX,int p_iY)
- {
- if (isExistPosInSameAreaList(p_iX,p_iY))
- return 0;
-
- g_SameAreaList[g_iSameAreaCount][0] = p_iX;
- g_SameAreaList[g_iSameAreaCount][1] = p_iY;
- g_iSameAreaCount++;
-
- return g_iSameAreaCount;
- }
- int GetSameArea(int p_iX,int p_iY)
- {
- int iNewX,iNewY;
- int iHasSame = 0;
- for (int d=0;d<4;d++)
- {
- iNewX = p_iX + dir[d][0];
- iNewY = p_iY + dir[d][1];
-
- if ( (iNewX>=0) && (iNewX<XSIZE) && (iNewY>=0) && (iNewY<YSIZE) )
- { //新的位置有效
- if (Map[iNewY][iNewX]==Map[p_iY][p_iX])
- {
- iHasSame = 1;
- if (AddOnePosToSameAreaList(iNewX,iNewY)!=0) //追加成功一個(gè)新的節(jié)點(diǎn)
- if (GetSameArea(iNewX,iNewY)==0)//再查詢(xún)下一個(gè)節(jié)點(diǎn)
- return 0;
- }
- }
- }
-
- return iHasSame;
- }
- int GetSameAreaList(int x,int y)
- { //從map中得到一片相連的區(qū)域,存放到 listSameArea
- g_iSameAreaCount = 0;
- return GetSameArea(x,y);
- }
- int GetShortStepCount(int x1,int y1,int x2,int y2,int p_iStep)
- {
- int iNewX,iNewY;
- // int iStepCount = 0;
- int iTemp;
-
-
-
- for (int d=0;d<4;d++)
- {
- iNewX = x1 + dir[d][0];
- iNewY = y1 + dir[d][1];
-
- if ( (iNewX>=0) && (iNewX<XSIZE) && (iNewY>=0) && (iNewY<YSIZE) ) { //新的位置有效
- if (Map[iNewY][iNewX]==Map[x1][y1]) {
- if ((iNewX==x2) && (iNewY==y2))
- return p_iStep;
-
- iTemp = GetShortStepCount(iNewX,iNewY,XSIZE-1,YSIZE-1,p_iStep);
- if (iTemp==9999)
- Map[iNewX][iNewY] = 100;
-
- p_iStep+=iTemp;
- }
- }
- }
-
- Map[y1][x1] = 100;
- return 9999;
- }
- int GetShortPathList()
- {
- int iNewX,iNewY;
- int iIndex;
- int i,d,x,y;
-
-
- Map[0][0] = 1;
-
- while (Map[YSIZE-1][XSIZE-1]==0) {
- for (y=0;y<YSIZE;y++)
- {
- for (x=0;x<XSIZE;x++)
- {
- if (Map[y][x]==DIE)
- continue;
-
- if (Map[y][x]==0)
- continue;
-
- for (d=0;d<4;d++)
- {
- iNewX = x + dir[d][0];
- iNewY = y + dir[d][1];
- if ( (iNewX>=0) && (iNewX<XSIZE) && (iNewY>=0) && (iNewY<YSIZE) ) { //新的位置有效
- if (Map[iNewY][iNewX]==DIE)
- continue;
-
- if (Map[iNewY][iNewX]==0)
- Map[iNewY][iNewX] = Map[y][x] + 1;
- else if (Map[iNewY][iNewX]>(Map[y][x] + 1))
- Map[iNewY][iNewX] = Map[y][x] + 1;
- }
- }
- }
- }
- }
-
- iIndex = 0;
-
- iIndex = 0;
- x = XSIZE-1;
- y = YSIZE-1;
- g_ShortPathList[iIndex][0] = x;
- g_ShortPathList[iIndex][1] = y;
- iIndex++;
- while(1) {
- if ( (x==0) && (y==0) )
- break;
-
- for (d=0;d<4;d++)
- {
- iNewX = x + dir[d][0];
- iNewY = y + dir[d][1];
- if ( (iNewX>=0) && (iNewX<XSIZE) && (iNewY>=0) && (iNewY<YSIZE) ) { //新的位置有效
- if (Map[iNewY][iNewX]==(Map[y][x]-1)) {
- g_ShortPathList[iIndex][0] = iNewX;
- g_ShortPathList[iIndex][1] = iNewY;
- iIndex++;
- x = iNewX;
- y = iNewY;
- break;
- }
- }
- }
- }
-
- g_iShortPathCount = iIndex;
- return g_iShortPathCount;
- }
- void ShowSameArea()
- {
- for (int i=0;i<g_iSameAreaCount;i++)
- {
- Map[g_SameAreaList[i][1]][g_SameAreaList[i][0]] = 10;
- }
-
- ShowMap();
- }
- int GetPathCount(int p_iX,int p_iY)
- {//得到一個(gè)節(jié)點(diǎn)的通路個(gè)數(shù)
- int iNewX,iNewY;
- int iPathCount = 0;
- for (int d=0;d<4;d++)
- {
- iNewX = p_iX + dir[d][0];
- iNewY = p_iY + dir[d][1];
-
- if ( (iNewX>=0) && (iNewX<XSIZE) && (iNewY>=0) && (iNewY<YSIZE) ) { //新的位置有效
- if (Map[iNewY][iNewX]==1)
- iPathCount++;
- else if (Map[iNewY][iNewX]==0)
- iPathCount++;
- }
- }
- return iPathCount;
- }
- int DropAllLeaf()
- {
- int iCount;
-
- //刪除單一葉子結(jié)點(diǎn)
- do {
- iCount = 0;
-
- for (int i=0;i<g_iSameAreaCount;i++)
- {
- if (GetPathCount(g_SameAreaList[i][0],g_SameAreaList[i][1])<=1)
- {
- Map[g_SameAreaList[i][1]][g_SameAreaList[i][0]] = 254;
- g_SameAreaList[i][0] = 0;
- g_SameAreaList[i][1] = 0;
- iCount++;
- }
- }
- } while(iCount>0);
-
- return iCount;
- //刪除兩個(gè)分支的結(jié)點(diǎn)
- }
- int DropDoubleLeaf()
- {
- int SameAreaList[YSIZE*XSIZE][2]; //相同區(qū)域的列表
- // int iSameAreaCount = 0;
- for (int i=0;i<g_iSameAreaCount;i++)
- {
- memcpy((char *)SameAreaList,g_SameAreaList,YSIZE*XSIZE*2*sizeof(int));
- // iSameAreaCount = g_iSameAreaCount;
- if (GetPathCount(g_SameAreaList[i][0],g_SameAreaList[i][1])==2)
- { //有兩條分支
- Map[g_SameAreaList[i][1]][g_SameAreaList[i][0]] = 254;
- g_SameAreaList[i][0] = 0;
- g_SameAreaList[i][1] = 0;
- // iCount++;
- }
- }
- return 0;
- }
- void init()
- {
- xx=0,yy=0;
- oldxx=xx,oldyy=yy;
- count = 0;
-
-
- // highvideo(void);
- // lowvideo(void);
- // normvideo(void);
- clrscr();
- clrscr();
- _setcursortype(_NOCURSOR);
- }
- void end()
- {
- // highvideo(void);
- // lowvideo(void);
- // normvideo(void);
-
- textattr(0x07);
- clrscr();
- _setcursortype(_NORMALCURSOR);
- }
- void main()
- {
- int i;
- // highvideo();
- textmode(64);
-
- end();
- init();
-
- lab_begin:
-
-
- end();
- init();
- MakeMap();
-
- GetSameAreaList(1,1);
-
- if (!isExistPosInSameAreaList(XSIZE-1,YSIZE-1)) {
- gotoxy(70,5);
- textattr(0xee);
- cprintf("disconnect!");
- gotoxy(70,6);
- textattr(0xee);
- cprintf("Esc to Exit");
- sound(500);
- delay(100);
- sound(250);
- delay(100);
- sound(500);
- delay(100);
- nosound();
-
- ShowSameArea();
- // ShowMap();
- // getch();
- delay(1000);
-
- goto lab_begin;
- }
-
- // ShowSameArea();
-
- for (i=0;i<g_iSameAreaCount;i++)
- Map[g_SameAreaList[i][1]][g_SameAreaList[i][0]] = 0;
- /*
- g_iShortPathCount = LineDDA(0,0,XSIZE-1,YSIZE-1,g_ShortPathList); // 最段的路徑點(diǎn)列表
- printf("\n%d\n",g_iShortPathCount);
- */
-
- g_iShortPathCount = 0 ;
- GetShortPathList();
-
- for (i=0;i<g_iSameAreaCount;i++)
- Map[g_SameAreaList[i][1]][g_SameAreaList[i][0]] = 1;
-
- for (i=0;i<g_iShortPathCount;i++) {
- if (Map[g_ShortPathList[i][1]][g_ShortPathList[i][0]]!=DIE)
- Map[g_ShortPathList[i][1]][g_ShortPathList[i][0]] = 0;
- }
-
- /*
- g_iShortPathCount = 0 ;
- // GetShortPathList();
- g_iShortPathCount = LineDDA(0,0,XSIZE-1,YSIZE-1,g_ShortPathList); // 最段的路徑點(diǎn)列表
- for (i=0;i<g_iShortPathCount;i++) {
- if (Map[g_ShortPathList[i][1]][g_ShortPathList[i][0]]!=DIE)
- Map[g_ShortPathList[i][1]][g_ShortPathList[i][0]] = 0;
- }
- */
- // delay(2000);
- ShowMap();
-
- do
- {
- Go();
-
- //ShowMap();
- ShowMan();
- ShowXY();
-
- if (Success()==0)
- {
- delay(1000);
- end();
- goto lab_begin;
- // return;
- }
-
- delay(50);
-
- }while(!kbhit());
- if (getch()!=27)
- goto lab_begin;
-
- _setcursortype(_NORMALCURSOR);
- clrscr();
- // normvideo();
- textmode(-1);
- }
- /*
- 20:05 2005-9-9
- 今天是周末,沒(méi)很多事,抽空研究了一下搜索算法.因?yàn)榍皫滋烊フ搲吹接芯W(wǎng)友請(qǐng)教迷宮算法的問(wèn)題,我把很久以前寫(xiě)的
- 一個(gè)走迷宮的程序貼上去了.這個(gè)程序比較土,不會(huì)判斷隨機(jī)產(chǎn)生的迷宮是否能走通,不是按最短路徑搜索,但是,只要是
- 能連通的迷宮就肯定能走出去.呵呵,我的算法沒(méi)學(xué)好,很多時(shí)候就搞自已瞎琢磨了.
- 以前的程序算法是這樣的:
-
- 1.隨機(jī)產(chǎn)生由0x00和0xff結(jié)成的地圖
- 2.從(0,0)點(diǎn)開(kāi)始進(jìn)入迷宮
- 3.因?yàn)槌隹谠?MAXX,MAXY),所以搜索方向是 右->下->上->左
- 4.每走過(guò)一個(gè)方格把此方格對(duì)應(yīng)的值加1
- 5.在選擇方向時(shí),總是優(yōu)先選擇方格值最小的相鄰方格,這樣,一個(gè)方格走過(guò)的次數(shù)越多就越不會(huì)再次走入,
- 所以自然而然就會(huì)走到(MAXX,MAXY)了
- 這種算法導(dǎo)致"小人"會(huì)在迷宮里不停的走來(lái)走去,很多時(shí)候是在重復(fù)走動(dòng),看起來(lái)傻傻的(俺喜歡)
- 為了解決判斷迷宮是否能走通問(wèn)題,和求最短路徑問(wèn)題,我想了很久.
- 嫌型閹悼梢雜肁*算法來(lái)探路比較好,我去找了幾篇資料,沒(méi)看太懂,
- 自已瞎折騰一通,又搞出一個(gè)新算法,也不知道學(xué)名叫什么,反正結(jié)果看起來(lái)是對(duì)的.呵呵
- 新的算法是這樣的:
- 1.隨機(jī)產(chǎn)生由0x00和0xff結(jié)成的地圖
- 2.建立一個(gè)空的"連通地圖方格列表",然后用遞歸方法去搜索所有與(0,0)相同值的方格,然后把坐格存入"連通地圖方格列表"中
- 在遞歸時(shí),如果碰到"連通地圖方格列表"中已經(jīng)存在的方格則跳出.這樣,就產(chǎn)生了一個(gè)"連通地圖方格列表",然后只要
- 判斷迷宮入口坐標(biāo)(0,0)和出口坐標(biāo)(MAXX,MAXY)是否都在列表時(shí)就可以知道是否迷宮能走通了,好簡(jiǎn)單吧:)
- 3.把迷宮入口坐標(biāo)(0,0)的賦值為1,然后用雙重循環(huán)判斷迷宮中每一方格,如果一個(gè)方格的值>1且小于255的話(huà),則把相鄰
- 的方格值全部加1,如果某一個(gè)相鄰方格的值比所在方格值+1還要大的話(huà)(因?yàn)檫B通的原因),則把相鄰方格設(shè)成方格值+1
- 重復(fù)這樣做,直到 出口坐標(biāo)(MAXX,MAXY) 也被賦值為止.
- 4.現(xiàn)在工作就很簡(jiǎn)單了,從出口坐標(biāo)(MAXX,MAXY)開(kāi)始向上推,逐次遞減直到入口坐標(biāo)(0,0),這樣就得到了一個(gè)由多個(gè)
- 坐標(biāo)組成的路線(xiàn)表,也就是最短路徑了(看起來(lái)是的)
- 5.因?yàn)槭窃诶系某绦蚧A(chǔ)上改的,也沒(méi)有仔細(xì)弄,把最短路徑經(jīng)過(guò)方格全部設(shè)為0,把其它連通的方格則全部設(shè)為1,
- 這樣老的程序不做什么修改就OK了.
- 6.欣賞了幾十遍小人走通迷宮的路線(xiàn),直是簡(jiǎn)潔,呵呵.
- 嗯,程序雖然表面上功能是實(shí)現(xiàn)了,但不知道這樣處理是不是會(huì)有漏洞.
-
- 算法書(shū)上的公式都看不懂,郁悶.
- */
復(fù)制代碼
|