답안 #864278

# 제출 시각 아이디 문제 언어 결과 실행 시간 메모리
864278 2023-10-22T09:57:55 Z danikoynov Event Hopping (BOI22_events) C++14
0 / 100
280 ms 21196 KB
#include<bits/stdc++.h>

using namespace std;

const int maxn = 1e5 + 10;
     
struct interval
{
    int s, e, idx;
}seg[maxn];
     
struct query
{
    int start, finish, idx;
}task[maxn];

bool cmp_finish(query q1, query q2)
{
    return q1.finish < q2.finish;
}
int n, q;   


void input()
{
    cin >> n >> q;
    for (int i = 1; i <= n; i ++)
    {
        cin >> seg[i].s >> seg[i].e;
        seg[i].idx = i;
    }
    for (int i = 1; i <= q; i ++)
    {
        cin >> task[i].start >> task[i].finish;
        task[i].idx = i;
    }
}



bool cmp_end(interval seg1, interval seg2)
{
    return seg1.e < seg2.e;
}

int lf[maxn], rev[maxn], rf[maxn], ans[maxn];
map < int, int > fix;
void build_graph()
{
    sort(seg + 1, seg + n + 1, cmp_end);
    for (int i = 1; i <= n; i ++)
    {
        rev[seg[i].idx] = i;
    }

    for (int i = 1; i <= n; i ++)
    {
        int l = 1;
        int r = i;
        while(l <= r)
        {
            int m = (l + r) / 2;
            if (seg[m].e < seg[i].s)
                l = m + 1;
            else
                r = m - 1;
        }
        lf[i] = l;
        //while(seg[lf[i]].e < seg[i].s)
           // lf[i] ++;


        if (fix[seg[i].e] == 0)
            fix[seg[i].e] = lf[i];
        else
            fix[seg[i].e] = min(fix[seg[i].e], lf[i]);
    }
}

const int maxlog = 21;
int dp[maxlog][maxn];

void answer_queries()
{
    for (int i = 1; i <= q; i ++)
    {
        task[i].start = rev[task[i].start];
        task[i].finish = rev[task[i].finish];
    }
    sort(task + 1, task + q + 1, cmp_finish);
    /**cout << "----------------------" << endl;
    for (int i = 1; i <= n; i ++)
        cout << seg[i].s << " :: " << seg[i].e << endl;*/
    vector < int > viable;

    int pt = 1;
    for (int i = 1; i <= q; i ++)
    {

        int st = task[i].start, en = task[i].finish;

        while(pt <= en)
        {
            
            while(!viable.empty() && lf[viable.back()] >= lf[pt])
                viable.pop_back();
            
            int l = 0, r = (int)(viable.size()) - 1;
            while(l <= r)
            {
                int m = (l + r) / 2;
                if (viable[m] < lf[pt])
                    l = m + 1;
                else
                    r = m - 1;
            }
            if (l >= viable.size())
                dp[0][pt] = pt;
            else
                dp[0][pt] = viable[l];

            for (int j = 1; j < maxlog; j ++)
            {
                dp[j][pt] = dp[j - 1][dp[j - 1][pt]];
            }

            viable.push_back(pt);
            
            pt ++;
        }
    if (st == en)
        {
            ans[task[i].idx] = 0;
            continue;
        }
        if (seg[st].e == seg[en].e && st != en)
        {
            ans[task[i].idx] = 1;
            continue;
        }
        
        if (st > en)
        {
            ans[task[i].idx] = -1;
            continue;
        }

        if (st >= lf[en])
        {
            ans[task[i].idx] = 1;
            continue;
        }

        
    
        int to = fix[seg[en].e];
        for (int i = lf[en]; i <= en; i ++)
            to = min(to, lf[i]);
        int steps = 1;

        bool done = false;
        int cur = viable.size() - 1;
      
        while(cur >= 0 && viable[cur] >= to)
            cur --;
        cur ++;
        if (lf[viable[cur]] >= to)
        {
            ans[task[i].idx] = -1;
                continue;
        }
        steps ++;
        
        int jump = 0, ver = viable[cur];
        if (st >= lf[ver])
        {
       
            ans[task[i].idx] = steps + 1;
            continue;
        }
        ///cout << "here " << task[i].idx << endl;
        for (int bit = maxlog - 1; bit >= 0; bit --)
        {
            if (lf[dp[bit][ver]] > st)
            {
                ver = dp[bit][ver];
                jump |= (1 << bit);
            }
        }

        jump ++;
        ver = dp[0][ver];
        
        if (st >= lf[ver])
        {
            ///cout << "HERE " << task[i].idx << endl;
            ans[task[i].idx] = steps + jump + 1;
        }
        else
        {
            ans[task[i].idx] = -1;
        }

        
            

            


    }

    for (int i = 1; i <= q; i ++)
    {
        if (ans[i] != - 1)
            cout << ans[i] << endl;
        else
            cout << "impossible" << endl;
    }
}
void solve()
{  
    input();
    build_graph();
    answer_queries();
}

int main()
{   
    ///speed();
    solve();

    return 0;
}

Compilation message

events.cpp: In function 'void answer_queries()':
events.cpp:117:19: warning: comparison of integer expressions of different signedness: 'int' and 'std::vector<int>::size_type' {aka 'long unsigned int'} [-Wsign-compare]
  117 |             if (l >= viable.size())
      |                 ~~^~~~~~~~~~~~~~~~
events.cpp:161:14: warning: unused variable 'done' [-Wunused-variable]
  161 |         bool done = false;
      |              ^~~~
# 결과 실행 시간 메모리 Grader output
1 Correct 2 ms 10588 KB Output is correct
2 Correct 256 ms 18356 KB Output is correct
3 Correct 266 ms 21196 KB Output is correct
4 Incorrect 280 ms 21136 KB Output isn't correct
5 Halted 0 ms 0 KB -
# 결과 실행 시간 메모리 Grader output
1 Incorrect 1 ms 10588 KB Output isn't correct
2 Halted 0 ms 0 KB -
# 결과 실행 시간 메모리 Grader output
1 Incorrect 1 ms 10588 KB Output isn't correct
2 Halted 0 ms 0 KB -
# 결과 실행 시간 메모리 Grader output
1 Incorrect 1 ms 10588 KB Output isn't correct
2 Halted 0 ms 0 KB -
# 결과 실행 시간 메모리 Grader output
1 Correct 278 ms 18264 KB Output is correct
2 Correct 269 ms 21068 KB Output is correct
3 Incorrect 278 ms 21136 KB Output isn't correct
4 Halted 0 ms 0 KB -
# 결과 실행 시간 메모리 Grader output
1 Correct 2 ms 10588 KB Output is correct
2 Correct 256 ms 18356 KB Output is correct
3 Correct 266 ms 21196 KB Output is correct
4 Incorrect 280 ms 21136 KB Output isn't correct
5 Halted 0 ms 0 KB -