hdu1026(bfs + priority_queue + 寻找路径)

题目地址:http://acm.hdu.edu.cn/showproblem.php?pid=1026

题目本身不复杂,不过输出路径比较麻烦,不过又想练习用下优先队列,所以有了以下的代码:

<span style="font-size:18px;">#include <iostream>
#include <algorithm>
#include <cstdio>
#include <cstring>
#include <string>
#include <queue>
using namespace std;
#define LL long long
int flag[105][105];
struct  node            //自定义结构的优先队列实现
{
    int x, y,step,f,index;
    int distance;
    friend bool operator < (node c, node b)
    {
        return c.step > b.step;//结构体中,x小的优先级高
    }
}a[10005];
int drX[4] = {0,0,1,-1};
int drY[4] = {1,-1,0,0};
int ans[10005];
int q;
char s[105][105];
void pnt(int index,int step)
{
    if(a[index].f != -1)
    {
        if(s[a[index].x][a[index].y] == '.')
        {
            pnt(a[index].f,step - 1);
            printf("%ds:(%d,%d)->(%d,%d)\n",step,a[a[index].f].x,a[a[index].f].y,a[index].x,a[index].y);
        }
        else
        {
            int time = s[a[index].x][a[index].y] - '0';
            pnt(a[index].f,step - 1 - (s[a[index].x][a[index].y] - '0'));
            printf("%ds:(%d,%d)->(%d,%d)\n",step - time,a[a[index].f].x,a[a[index].f].y,a[index].x,a[index].y);
            for(int i = 0;i < time;i++)
            {
                printf("%ds:FIGHT AT (%d,%d)\n",step + i - time + 1,a[index].x,a[index].y);
            }
        }
    }
}
int main()
{
    int n,m,k;
    priority_queue <node> pq;
    while(cin >> n >> m)
    {
        for(int i = 0;i < n;i++)
        {
            scanf("%s",s[i]);
        }
        while(pq.empty() == false) pq.pop();
        memset(flag,0,sizeof(flag));
        int pre = 0,rear = 1,nextX,nextY,ans;
        a[0].distance = n + m - 2; a[0].step = 0;
        a[0].x = 0; a[0].y = 0; a[0].f = -1; a[0].index  = 0;
        pq.push(a[0]);
        struct node tmp;
        flag[0][0] = 1;
        q = 0;
        bool sign = true;
        while(pq.empty() == false && sign == true)
        {
            tmp = pq.top();
            pq.pop();
            for(int i = 0;i < 4;i++)
            {
                nextX = tmp.x + drX[i];
                nextY = tmp.y + drY[i];
                if(nextX >= 0 && nextY >= 0 && nextX < n && nextY < m && s[nextX][nextY] != 'X' && flag[nextX][nextY] == 0)
                {
                    flag[nextX][nextY] = 1;
                    if(nextX == n - 1 && nextY == m - 1)
                    {
                        ans = tmp.step + 1;
                        if(s[nextX][nextY] != '.') ans += s[nextX][nextY] - '0';
                        printf("It takes %d seconds to reach the target position, let me show you the way.\n",ans);
                        if(s[nextX][nextY] == '.') pnt(tmp.index,ans - 1);
                        else pnt(tmp.index,ans - (s[nextX][nextY] - '0') - 1);
                        if(s[nextX][nextY] != '.')
                        {
                            int time = s[nextX][nextY] - '0';
                            printf("%ds:(%d,%d)->(%d,%d)\n",ans - time,tmp.x,tmp.y,nextX,nextY);
                            for(int i = 0;i < time;i++)
                            {
                                printf("%ds:FIGHT AT (%d,%d)\n",ans + i - time + 1,nextX,nextY);
                            }
                        }
                        else
                        {
                            printf("%ds:(%d,%d)->(%d,%d)\n",ans,tmp.x,tmp.y,nextX,nextY);
                        }
                        puts("FINISH");
                        sign = false;
                        break;
                    }
                    else
                    {
                        a[rear].x = nextX;
                        a[rear].y = nextY;
                        a[rear].step = tmp.step + 1;
                        if(s[nextX][nextY] != '.') a[rear].step += (s[nextX][nextY] - '0');
                        a[rear].f = tmp.index;
                        a[rear].index = rear;
                        a[rear].distance = (n - 1 - nextX) + (m - 1 - nextY);
                        pq.push(a[rear++]);
                    }
                }
            }
        }
        if(sign == true)
        {
            printf("God please help our poor hero.\nFINISH\n");
        }
    }
    return 0;
}
</span>


评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值