0
点赞
收藏
分享

微信扫一扫

AcWing——1726.挤奶顺序

天蓝Sea 2022-03-30 阅读 61
c++算法

本题想起来并不难想,就是分情况讨论嘛~,但是吧就是代码实现起来有些复杂
先说一下我最开始怎么想的,纯暴力 思路如下
先把位置确定的先用b数组存一下,如果 奶牛1 的位置确定直接输出结果然后return即可,否则把相对顺序确定的m[i] 插入到里面,如果 奶牛1 在这个序列里面,就从前往后遍历找 奶牛1 的最小插入位置输出结果即可,然后剩余的下标最小的位置就是 奶牛1 的位置,从前往后遍历一遍找打第一个b[i]==0即为 奶牛1 的位置.

当然既然说了刚开始怎么想的,那刚开始的思路肯定很混乱,代码的话写出来了但是不太对,然后就重新捋了一下思路:
可分为三种情况:

  1. 奶牛1 的位置已经确定给出,直接输出答案 return
  2. 奶牛1 的位置在m[i]中给出,判奶牛1 前面已经确定的位置然后从前往后遍历,把m[i]填入b[i],找 奶牛1 的最近位置.
  3. 奶牛1 的位置在剩余序列中,就是从后往前遍历填入m[i],然后从前往后遍历b[i],第一个为空的b[i]即为答案,输出 i 即可.

代码如下:

#include <iostream>
#include <cstring>
#include <algorithm>
using namespace std;
const int N = 110;
int a[N];//m[N]
int st[N];//标记第p[i]位是否有奶牛
int b[N];//对应排好序的奶牛序列
int flag;
int main()
{
    int n,m,k;
    cin>>n>>m>>k;
    for(int i=1;i<=m;i++)
    {
        cin>>a[i];
        if(a[i]==1) flag=1;//判断奶牛1在不在a[i]里面(与题上的m[i]等价)
    }
    memset(b, -1, sizeof b);
    while(k--)
    {
        int c,p;
        cin>>c>>p;
        if (c == 1)
        {
            cout << p << endl;//第一种情况:奶牛1的位置已确定
            return 0;
        }
        b[c]=p;
        st[p]=1;
    }
    if(flag)//第二种情况:奶牛在a[i](m[i])中
    {
        for(int i=1,j=1;i<=m;i++)
        {
            while(st[j]) j++;
            if(b[a[i]]!=-1) j=b[a[i]];
            else 
            {
                if(a[i]==1)
                {
                    cout<<j<<endl;
                    return 0;
                }
                st[j]=1;
                j++;
            }
        }
    }
    else//第三种情况:奶牛1在剩下的位置里面
    {
        for(int i=m,j=n;i;i--)
        {
            while(st[j]) j--;
            if(b[a[i]]!=-1) j=b[a[i]];
            else 
            {
                st[j]=1;
                j--;
            }
        }
        for(int i=1;i<=n;i++)
        {
            if(st[i]==0)
            {
                cout<<i<<endl;
                return 0;
            }
        }
    }
    return 0;
}
举报

相关推荐

acwing 122

传送AcWing

acwing 170

acwing 120

acwing 341

0 条评论