寻路算法:广度寻路

7 篇文章 0 订阅
3 篇文章 0 订阅

1.介绍
广度寻路算法是上,左,下,右一起试探,把试探过能走的点用以四叉树的方式保存起来,直到试探到终点。
广度相比于深度,可以找到从起点到终点的最佳路径

废话不多说,看图
2.图
在这里插入图片描述
图中1表示起点,2表示终点
在这里插入图片描述

3.步骤&&方法:
1.如上图,这里引入一个层的概念,例如起点(1,9)就是第一层,随之试探出第二层…
2.这里可以使用C++的vector,把第一层的节点存入vector中,在进行循环,在之后吧第一层的每一个节点试探出的节点存放到vect中,直到试探出终点循环结束。

4.代码

#include"stdfax.h"
#define ROW  10
#define COL  10


//枚举
enum direct { p_Up, p_Left, p_Down, p_Right };

class testMap
{
public:
	bool IsGo;//是否走过
};

struct MyPoint
{
	int x;
	int y;
	
};

class treeNode
{
public:
	//数据域
	MyPoint pos;
	//指针域
	treeNode * Parent;                  //指向上一层的指针
	vector<treeNode *> pChild;          //指向下一层的指针
	treeNode(int x,int y)
	{
		pos.x = x;
		pos.y = y;
		Parent  = NULL;
	}

	treeNode(MyPoint pos1)
	{
		pos = pos1;
		Parent  = NULL;
	}
}; 
//试试能不能走
bool CanWalk(int map[ROW][COL], testMap testmap[ROW][COL],MyPoint pos)
{
	//是障碍
	if (map[pos.x][pos.y] ) return false;

	//已经走过
	if (testmap[pos.x][pos.y].IsGo == true) return false; 

	//不在地图内
	if (pos.x >= ROW || pos.x < 0 || pos.y >= COL || pos.y < 0) return false;

	return true;
}

int main()
{
     //1.准备一个地图
	int map[ROW][COL] = {
		1,1,1,1,1,1,1,1,1,1,
		1,0,1,0,0,0,0,1,1,1,
		1,0,0,0,1,1,1,1,1,1,
		1,0,0,0,0,0,0,0,1,1,
		1,0,1,1,1,1,1,0,1,1,
		1,0,0,0,0,1,1,0,1,1,
		1,0,1,0,1,1,1,0,1,1,
		1,0,0,0,1,1,0,0,1,1,
		1,0,0,0,0,0,0,0,0,1,
		1,1,1,1,1,1,1,1,1,1
	};
	//2.准备一个测试地图
	testMap testmap[ROW][COL] = { 0 };

	//3.初始化起点和终点
	MyPoint BegPoint = { 1,1 };       //起点
	MyPoint EndPoint = { 8,2 };       //终点

	testmap[BegPoint.x][BegPoint.y].IsGo = true;//标记起始点已经走过

	vector<treeNode *> Current;       //用于储存当前层的节点
	vector<treeNode *> Next;          //用于储存下一层的节点

	treeNode * pRoot = new treeNode(BegPoint); //起点节点当做树的根
	Current.push_back(pRoot);//吧树的节点存放到当前层中

	MyPoint tempPos;                 

	//3.寻路
	MyPoint currentPos;               //用于表示当前点
	treeNode * pChild = NULL;         //专门用来存储新节点

	bool IsEnd = false;                       //判断是不是终点
	while (1)
	{
		//printf("666");
		//清除下一层
		Next.clear();

		//表示当前层的循环
		for (int i = 0; i < Current.size(); i++)
		{
			currentPos = Current[i]->pos;    //当前点等于当前层中第i个节点的点
		    //开始走
			for (int j = 0; j < 4;j++)
			{
				switch (j)
				{
				case p_Up://向上
					tempPos.x = currentPos.x;
					tempPos.y = currentPos.y - 1;
					break;
				case p_Left://左
					tempPos.x = currentPos.x-1;
					tempPos.y = currentPos.y;
					break;
				case p_Down://向下
					tempPos.x = currentPos.x;
					tempPos.y = currentPos.y + 1;
					break;
				case p_Right://向右
					tempPos.x = currentPos.x + 1;
					tempPos.y = currentPos.y;
					break;

				default:
					break;
				}
				//判断是不是能走
				if (CanWalk(map,testmap, tempPos))
				{
					//1.开辟新内存
					pChild = new treeNode(tempPos);
					//2.节点入树
					Current[i]->pChild.push_back(pChild);
					//3.保存到下一层(Next)中
					Next.push_back(pChild);

					//4.新节点的Parent指针指向上一层节点
					pChild->Parent = Current[i];

					//5.标记已经走过
					testmap[tempPos.x][tempPos.y].IsGo = true;

					//如果是终点
					if (tempPos.x == EndPoint.x && tempPos.y == EndPoint.y)
					{
						IsEnd = true;
						break;
					}
				}
				if (IsEnd)
					break;
			}//end of(j)
			if (IsEnd)
				break;
		}//end of(i)		
		if (IsEnd)
		{
			printf("找到终点啦");
			while (NULL != pChild)
			{
				printf("路径是:");
				printf("(%d,%d)\n ", pChild->pos.x, pChild->pos.y);
				pChild = pChild->Parent;
			}
			break;
		}
		//当前层切换到下一层
		Current = Next;
	}

	printf("程序结束\n");

	return 0;
}

5.总结
1.广度与深度的比较
1.1.没有回退
1.2.深度不一定能找到最佳路径,广度能
1.3.时间复杂度高
2.个人感觉广度寻路算法要比深度寻路算法要有趣的多。像RPG游戏里的自动寻路用的就是类似于广度的算法吧。比如A星寻路就是在广度的基础上更加智能优化了一点。

明天继续更新A星寻路算法,前几天因为开学原因没时间啦。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值