[3] A strange lift

题意:有一个奇怪的电梯,他可以停在任何一层,并且在每个楼层有一个Ki(0 <= Ki <= N)。电梯只有两个按钮:上、下。当你在第i层,如果你按下“UP”按钮,你将上升Ki层,也就是说,你将会到达第i+Ki层,如果你按下“DOWN”按钮,你会下降 Ki层,即您将前往第i-Ki层。当然,电梯不能高于N,也不能低于1。每次先输入层数N,并输入起始点和目标点,接下来N行输入每层的值,输入0结束程序,输出最少运行的次数,若无可能,输出-1。

算法:BFS

问题:第一次学习bfs算法。(注意:vis数组别忘了清空!!!找错找了好久)

思路:利用c++的queue,每次将同一层的数据依次存入队列,并将队列头保存后删除,查找队列头元素所对应的下一层,依次存入队列;重复上述操作,便可依次将该层的数据处理完,队列中便全部是下一层的了,随后进行相同操作,逐步处理下下层的数据。又因为本题所求为最小,定义vis数组标记是否走过。

代码:ac

#include<bits/stdc++.h>
using namespace std;
int N, Start, End;
int a[202];
int vis[202];
struct pos
{
    int level;/*所处层数*/
    int steps;/*按键次数*/
};
void bfs();
int main()
{
    while (scanf("%d", &N) == 1)
    {
        if (N == 0) break;
        scanf("%d%d", &Start, &End);
        for (int i = 1; i <= N; i++)
        {
            scanf("%d", &a[i]);
            vis[i] = 0;/*是否搜索过该节点*/
        }
        bfs();
    }
    return 0;
}
void bfs()
{
    pos cur, nex;/*curent和next*/
    cur.level = Start;
    cur.steps = 0;
    queue<pos>qu;
    qu.push(cur);/*在数列中加入该头节点*/
    vis[Start] = 1;
    while (!qu.empty())/*数列q非空情况下进行循环*/
    {
        cur = qu.front();/*先存数列头*/
        qu.pop();/*再删除*/
        if (cur.level == End)
        {
            printf("%d\n", cur.steps);/*因为是一层一层搜索的,所以找到就是最小值*/
            return;
        }
        nex.level = cur.level + a[cur.level];/*尝试向上走*/
        nex.steps = cur.steps + 1;/*状态转移*/
        if (nex.level <= N)/*判断是否越上界*/
        {
            if (vis[nex.level] == 0)
            {
                vis[nex.level] = 1;
                qu.push(nex);/*如果不越界,就将层数存入q数列*/
            }
        }
        nex.level = cur.level - a[cur.level];/*尝试向下走*/
        nex.steps = cur.steps + 1;
        if (nex.level >= 1)/*判断是否越下界*/
        {
            if (vis[nex.level] == 0)
            {
                vis[nex.level] = 1;
                qu.push(nex);/*同理*/
            }
        }
    }
    printf("-1\n");/*如果之前没有return,说明没有可能,输出-1*/
    return;
}

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 1
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值