利用广度优先遍历实现寻路

#include<stdio.h>
#include<stdlib.h>
#include<stdbool.h>
#include<graphics.h>//如果运行不了,看编译器是否安装Easyx库,如果没有安装可以去Easyx官网安装
typedef struct Queue
{
	int *Buff;
	int MAX;
	int front;
	int rear;
}Queue;
typedef struct Stack
{
	int* Buff;
	int Max;
	int top;
}Stack;
typedef struct Aim
{
	int x;
	int y;
}Aim;
enum MyEnum
{
   UP,
   DOWN,
   LEFT,
   RIGHT,
   UP_LEFT,
   UP_RIGHT,
   DOWN_LEFT,
   DOWN_RIGHT
};
Queue *Init_Queue(int Max)
{
	Queue* Temp = (Queue*)malloc(sizeof(Queue));
	if (!Temp)
		return NULL;
	Temp->MAX = Max;
	Temp->Buff = (int*)malloc(sizeof(int)*Max);
	if (Temp->Buff == NULL)
	{
		free(Temp);
		return NULL;
	}
	Temp->front = -1;
	Temp->rear = -1;
	return Temp;
}
Stack* Init_Stack(int Length)
{
	Stack* Temp = (Stack*)malloc(sizeof(Stack));
	if (Temp == NULL)
		return NULL;
	Temp->Buff = (int*)malloc(Length*sizeof(int));
	if (Temp->Buff == NULL)
	{
		free(Temp);
		return NULL;
	}
	Temp->Max = Length - 1;
	Temp->top = -1;
}
bool Empty_Stack(Stack* Temp)
{
	if (Temp->top == -1)
		return false;
	return true;
}
bool Push_Stack(Stack*Temp,int data)
{
	if (Temp->top == Temp->Max)
		return false;
	Temp->top++;
	Temp->Buff[Temp->top] = data;
	return true;
}

bool Pop_Stack(Stack*Temp,int *data)
{
	if (!Empty_Stack(Temp))
		return false;
	*data = Temp->Buff[Temp->top];
	Temp->top--;
	return true;
}
void Destroy_Stack(Stack*stack)
{
	free(stack->Buff);
	free(stack);
}
bool Empty_Queue(Queue*que)
{
	if (que == NULL)
		return false;
	if (que->front == que->rear)
		return false;
	return true;
}
bool Push_Queue(Queue* que,int data)
{
	if (que == NULL)
		return false;
	if ((que->rear+1)==que->front)
		return false;
	que->rear = (que->rear+1)%que->MAX;
	que->Buff[que->rear] = data;
	return true;
}
bool Pop_Queue(Queue* que, int *data)
{
	if (que == NULL)
		return false;
	if (!Empty_Queue(que))
		return false;
	que->front = (que->front + 1) % que->MAX;
	*data = que->Buff[que->front];
	return true;
}
void Destroy_Queue(Queue*que)
{
	free(que->Buff);
	free(que);
}
int *Map=NULL;
int Width = 0;
int Heigh = 0;
int size = 5;
inline bool Init_Map()
{
	Map = (int*)malloc(Width*Heigh*sizeof(int));
	if (Map == NULL)
		return false;
	return true;
}
inline bool Path(int y,int x,int Map[])
{
	if (Map[y* Width +x] == -1|| Map[y * Width + x] == -3)
		return true;
	return false;
}
//自动寻路
bool Find(Aim s,Aim e)
{
	int temp = 0;
	int Max_index = Heigh * Width-1;
	Queue* que = Init_Queue(Heigh * Width);
	if (que == NULL)
		return false;
	Push_Queue(que,s.y* Width +s.x);
	while (Pop_Queue(que, &temp))
	{
		int Sec = temp;
		//对上下左右进行寻路
		for (int i = 0; i < 8; i++)
		{
			switch (i)
			{
			case UP:
				Sec = temp - Width;
				break;
			case DOWN:
				Sec = temp + Width;
				break;
			case LEFT:
				if(temp% Width !=0)//防止位置越界
				Sec = temp - 1;
				break;
			case RIGHT:
				if (temp % Width != (Width - 1))//防止位置越界
				Sec = temp + 1;
				break;
			case UP_LEFT:
				if (temp % Width != 0)//防止位置越界
					Sec = (temp - 1) - Width;
				break;
			case UP_RIGHT:
				if (temp % Width != 0)//防止位置越界
					Sec = (temp - 1) + Width;
				break;
			case DOWN_LEFT:
				if (temp % Width != (Width - 1))//防止位置越界
					Sec = (temp + 1)-Width;
				break;
			case DOWN_RIGHT:
				if (temp % Width != (Width - 1))//防止位置越界
					Sec = (temp + 1) + Width;
				break;
			}
			//不是正常路径跳过
			if (Sec < 0 || Sec>Max_index)
				continue;
			//判断路径是否可以通过
			if (Path(Sec / Width, Sec % Width,Map))
			{//记录路径
				Map [Sec] = temp;
				Push_Queue(que,Sec);
				//判断是否是终点
				if (e.y == Sec / Width && e.x == Sec % Width)
				{
					Destroy_Queue(que);
					return true;
				}
			}
	    }
	}
	Destroy_Queue(que);
	return false;
}
inline void SetColor_XY(unsigned int color,int x,int y)
{
	setfillcolor(color);//设置边框颜色
	fillrectangle(x  * size, y * size, x * size + size, y * size + size);
}
//图像输出函数+控制台输出
void Prinf_Path(Aim s,Aim e)
{
  int temp = Map[e.y*Width+e.x];
  Stack* Temp_Stack = Init_Stack(Heigh * Width);
  Push_Stack(Temp_Stack, temp);
  printf("回溯顺序:\n");
  printf("[%d] [%d]\n", temp / Width, temp % Width);
  while(temp/ Width !=s.y||temp% Width !=s.x)
  { 
	  temp = Map[temp];
	  Push_Stack(Temp_Stack, temp);
	  printf("[%d] [%d]\n", temp / Width, temp % Width);
  }
  printf("出栈顺序:\n");
  int index = 0;
  while (Empty_Stack(Temp_Stack))
  {
	  if (Pop_Stack(Temp_Stack, &index))
	  {
		  printf("[%d] [%d]\n", index / Width, index % Width);
		  SetColor_XY(WHITE, index % Width, index / Width);
		  Sleep(100);
	  }
  }
  Destroy_Stack(Temp_Stack);
}
//图像输出函数
void DrawPath(int array[],int len)
{
	unsigned int color=0;
	BeginBatchDraw(); 
	for (int i=0;i<len;i++)
	{
		setlinecolor(BLUE);//设置边框颜色
		if (array[i] == -1)
			color = 0x00CD66;
		else
			color = RED;
		SetColor_XY(color,i%Width, i / Width);
	}
	EndBatchDraw();
}
//输入判断
void Scanf_Path(Aim *s,Aim *e)
{
	MOUSEMSG mouse;
	int index = 0;
	int x, y;
	DrawPath(Map, Width*Heigh);
	while (index<2)
	{
		mouse = GetMouseMsg();
		setlinecolor(BLUE);//设置边框颜色
		switch (mouse.uMsg)
		{
		case WM_LBUTTONDOWN:
			x = mouse.x / size;
			y = mouse.y / size;
			if(index==0)
			{
				if (Map[y * Width + x] == -1)
				{
					s->x = x;
					s->y = y;
					index++;
					Map[y * Width + x] = -2;
					printf("起点:[%d][%d]\n",y,x);
					SetColor_XY(0x065695, x, y);
				}
			}
			else if (index == 1)
			{
				if (Map[y * Width + x] == -1)
				{
					e->x = x;
					e->y = y;
					index++;
					Map[y * Width + x] = -3;
					printf("终点:[%d][%d]\n",y,x);
					SetColor_XY(WHITE, x, y);
				}
			}
			break;
		case WM_RBUTTONDOWN:
			unsigned int color = 0;
			x = mouse.x / size;
			y = mouse.y / size;
			if (Map [y*Width+x] == -1)
			{
				Map[y * Width + x] = 0;
				color = RED;
			}
			else if(Map[y * Width + x] == 0)
			{
				Map[y * Width + x] = -1;
				color = 0x00CD66;
			}
			if(color!=0)
			SetColor_XY(color,x,y);
			break;
		}
	}
}
void Find_Path()
{
	Aim s = { 0,0 };
	Aim e = { 0,0 };
	initgraph(Width* size, Heigh* size);
	Scanf_Path(&s, &e);
	if (Find(s, e))
	{
		printf("Finish\n");
		Prinf_Path(s, e);
	}
	else
		printf("Error\n");
	printf("数组元素:\n");
	for (int i = 0; i < Heigh; i++)
	{
		for (int j = 0; j < Width; j++)
			printf(" %4d", Map[i*Width+j]);
		printf("\n\n");
	}
}
int main()
{
	printf("请输入Width,Heigh,size:\n");
	while (scanf("%d %d %d", &Width, &Heigh,&size) == 0)
		char a=getchar();
	//数组初始化
	if(Init_Map())
	{
		while (1)
		{
			for (int i = 0; i < Heigh; i++)
				for (int j = 0; j < Width; j++)
					Map[i * Width + j] = -1;
			Find_Path();
			system("pause");
			//数组复位
		}
	}
	free(Map);
	return 0;
}

  • 2
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值