首先可以看出是按照奶牛的编号进行二分去寻找第一个没有礼物的奶牛。但如何验证某个编号的奶牛前面有死循环存在呢。
因为是从后面插空的所以会因为后面牛数量的改变而改变。但可以转化到插第几个位置,如果位置2上有两个及其以上的牛的目标都是它,那么就会造成死循环。同样如果3这个位置上有三个及其以上的牛目标都是他,也会造成死循环。
#include <bits/stdc++.h>


using namespace std;
const int maxn = 1e5+10;
int N, c[maxn];

bool yanz(int mid) {
    int b[maxn]={0};
    long long sum=0;
    for (int i=1;i<=mid;i++) {
        b[c[i]]++;
    }
    for (int i=1;i<=mid;i++) {
        sum += b[i];
        if (sum>=i) {
            return true;
        }
    }
    return false;
}

int main() {
    cin>>N;
    for (int i=1;i<=N;i++) {
        cin>>c[i];
        c[i] = N-c[i];
    }
    int l = 0, r = N;
    while (l<r) {
        int mid = (l+r)/2;
//         cout<<mid<<" "<<yanz(mid)<<endl;
        if (yanz(mid)) {
            r = mid;
        } else {
            l = mid+1;
        }
    }
    cout<<N-l;
    return 0;
}