Submission #1339879

#TimeUsernameProblemLanguageResultExecution timeMemory
1339879tudor_costinSuperpiece (EGOI22_superpiece)C++20
100 / 100
659 ms460 KiB
#include <bits/stdc++.h>
#define int long long
using namespace std;
const int dx[]={1,1,-1,-1,2,2,-2,-2};
const int dy[]={2,-2,2,-2,1,-1,1,-1};
const int dxK[]={1,1,1,0,-1,-1,-1,0};
const int dyK[]={-1,0,1,1,1,0,-1,-1};
const int bulanK=50,bulanP=1000,inf=LLONG_MAX;
int distN(int a,int b,int c,int d)
{
    int p=abs(a-c),q=abs(b-d);
    int paritate=(p+q)%2;
    int l=0,r=1e9;
    int ans=r;
    while(l<=r)
    {
        int mid=(l+r)/2;
        int B=2*mid+paritate;
        pair<int,int> intervy={0,min(B,2*B-p)};
        pair<int,int> intervx={0,min(B,2*B-q)};
        if(intervy.first%2!=p%2) intervy.first++;
        if(intervy.second%2!=p%2) intervy.second--;
        if(intervx.first%2!=q%2) intervx.first++;
        if(intervx.second%2!=q%2) intervx.second--;
        bool ok=1;
        if(intervy.first>intervy.second) ok=0;
        if(intervx.first>intervx.second) ok=0;
        if(!ok)
        {
            l=mid+1;
            continue;
        }
        ///check possible cu x=0
        if(intervx.first==0)
        {
            if(p<=B && p%2==B%2 && q<=2*B && q%4==((2*B)%4))
            {
                ans=B;
                r=mid-1;
                continue;
            }
        }
        ///check possible cu y=0
        if(intervy.first==0)
        {
            if(q<=B && q%2==B%2 && p<=2*B && p%4==((2*B)%4))
            {
                ans=B;
                r=mid-1;
                continue;
            }
        }
        ///nu luam x=0 sau y=0
        if(intervx.first==0) intervx.first=2;
        if(intervy.first==0) intervy.first=2;
        if(intervy.first>intervy.second) ok=0;
        if(intervx.first>intervx.second) ok=0;
        int low=intervy.first+intervx.first,high=intervx.second+intervy.second;
        if(B<low || B>high) ok=0;
        if(ok)
        {
            ans=B;
            r=mid-1;
        }
        else l=mid+1;
    }
    return ans;
}
bool samediag(int a,int b,int c,int d)
{
    return((a+b)==(c+d) || (a-b)==(c-d));
}
bool samerowcol(int a,int b,int c,int d)
{
    return (a==c || b==d);
}
bool canreachB(int a,int b,int c,int d)
{
    return (abs(a+b)%2==abs(c+d)%2);
}
pair<bool,vector<pair<int,int>>> cangetN(int a,int b,int c,int d,int moves)
{
    queue<pair<pair<int,int>,int>> q;
    vector<pair<int,int>> went;
    map<pair<int,int>,int> viz;
    q.push({{a,b},0});
    while(!q.empty())
    {
        auto[pi,dist]=q.front();
        q.pop();
        if(pi.first==c && pi.second==d)
        {
            return {true,went};
        }
        if(viz[pi]) continue;
        went.push_back(pi);
        viz[pi]=1;
        if(dist<moves)
        {
            for(int k=0;k<8;k++)
            {
                pair<int,int> nwpi=pi;
                nwpi.first+=dx[k];
                nwpi.second+=dy[k];
                if(!viz[nwpi])q.push({nwpi,dist+1});
            }
        }
    }
    return {false,went};
}
bool cangetK(int a,int b,int c,int d)
{
    return (abs(a-c)<=1 && abs(b-d)<=1);
}
bool cangetP(int a,int b,int c,int d)
{
    return (b==d && a==c+1);
}
int distK(int a,int b,int c,int d)
{
    return max(abs(a-c),abs(b-d));
}
int solveNKP(int a,int b,int c,int d,string s)
{
    if(s.empty()) return inf;
    if(s[0]=='N')
    {
        if(s=="N") return distN(a,b,c,d);
        if(s[1]=='K')
        {
            int ans=inf;
            for(int i=a-bulanK;i<=a+bulanK;i++)
            {
                for(int j=b-bulanK;j<=b+bulanK;j++)
                {
                    ans=min(ans,distN(i,j,c,d)+distK(a,b,i,j));
                    ///cout<<ans<<' '<<i<<' '<<j<<'\n';
                }
            }
            return ans;
        }
        if(s[1]=='P')
        {
            int ans=inf;
            for(int i=a;i<=a+bulanP;i++)
            {
                ans=min(ans,distN(i,b,c,d)+i-a);
            }
            return ans;
        }
    }
    if(s[0]=='K')
    {
        return distK(a,b,c,d);
    }
    if(s[0]=='P')
    {
        if(a>c || b!=d) return inf;
        else return (c-a);
    }
}
void solve()
{
    string s;
    cin>>s;
    int a,b,c,d;
    cin>>a>>b>>c>>d;
    if(a==c && b==d)
    {
        cout<<0<<'\n';
        return;
    }
    if(s[0]=='Q')
    {
        if(samediag(a,b,c,d) || samerowcol(a,b,c,d)) cout<<1<<'\n';
        else
        {
            bool hasN=0;
            for(auto ch:s) if(ch=='N') hasN=1;
            if(hasN && cangetN(a,b,c,d,1).first) cout<<1<<'\n';
            else cout<<2<<'\n';
        }
        return;
    }
    if(s[0]=='R')
    {
        if(samerowcol(a,b,c,d)) cout<<1<<'\n';
        else
        {
            for(auto ch:s)
            {
                if(ch=='B')
                {
                    if(samediag(a,b,c,d))
                    {
                        cout<<1<<'\n';
                        return;
                    }
                }
                if(ch=='N')
                {
                    if(cangetN(a,b,c,d,1).first)
                    {
                        cout<<1<<'\n';
                        return;
                    }
                }
                if(ch=='K')
                {
                    if(cangetK(a,b,c,d))
                    {
                        cout<<1<<'\n';
                        return;
                    }
                }
            }
            cout<<2<<'\n';
        }
        return;
    }
    if(s[0]=='B')
    {
        if(samediag(a,b,c,d)) cout<<1<<'\n';
        else if(canreachB(a,b,c,d))
        {
            for(auto ch:s)
            {
                if(ch=='N')
                {
                    if(cangetN(a,b,c,d,1).first)
                    {
                        cout<<1<<'\n';
                        return;
                    }
                }
                if(ch=='K')
                {
                    if(cangetK(a,b,c,d))
                    {
                        cout<<1<<'\n';
                        return;
                    }
                }
                if(ch=='P')
                {
                    if(cangetP(a,b,c,d))
                    {
                        cout<<1<<'\n';
                        return;
                    }
                }
            }
            cout<<2<<'\n';
            return;
        }
        else
        {
            bool hasOther=0;
            for(auto ch:s)
            {
                if(ch=='N')
                {
                    hasOther=1;
                    pair<bool,vector<pair<int,int>>> pi=cangetN(a,b,c,d,1);
                    if(pi.first)
                    {
                        cout<<1<<'\n';
                        return;
                    }
                }
                if(ch=='K')
                {
                    hasOther=1;
                    if(cangetK(a,b,c,d))
                    {
                        cout<<1<<'\n';
                        return;
                    }
                }
                if(ch=='P')
                {
                    hasOther=1;
                    if(cangetP(a,b,c,d))
                    {
                        cout<<1<<'\n';
                        return;
                    }
                }
            }
            string nws="";
            for(auto ch:s)
            {
                if(ch!='B')
                {
                    nws=nws+ch;
                }
                if(ch=='N')
                {
                    hasOther=1;
                    pair<bool,vector<pair<int,int>>> pi=cangetN(a,b,c,d,1);
                    for(auto [x,y]:pi.second)
                    {
                        if(samediag(x,y,c,d))
                        {
                            cout<<2<<'\n';
                            return;
                        }
                    }

                }
                if(ch=='K')
                {
                    hasOther=1;
                    for(int k=0;k<8;k++)
                    {
                        if(samediag(a+dxK[k],b+dyK[k],c,d))
                        {
                            cout<<2<<'\n';
                            return;
                        }
                    }
                }
                if(ch=='P')
                {
                    hasOther=1;
                    if(samediag(a+1,b,c,d))
                    {
                        cout<<2<<'\n';
                        return;
                    }
                }
            }
            int ans1=solveNKP(a,b,c,d,nws);
            if(hasOther) cout<<min(3LL,ans1)<<'\n';
            else cout<<-1<<'\n';
            return;
        }
        return;
    }
    int ans=solveNKP(a,b,c,d,s);
    if(ans!=inf) cout<<ans<<'\n';
    else cout<<-1<<'\n';
}
signed main()
{
    ios_base::sync_with_stdio(0);
    cin.tie(0),cout.tie(0);
    int t;
    cin>>t;
    while(t--)
    {
        solve();
    }
    return 0;
}

Compilation message (stderr)

Main.cpp: In function 'long long int solveNKP(long long int, long long int, long long int, long long int, std::string)':
Main.cpp:161:1: warning: control reaches end of non-void function [-Wreturn-type]
  161 | }
      | ^
#Verdict Execution timeMemoryGrader output
Fetching results...
#Verdict Execution timeMemoryGrader output
Fetching results...
#Verdict Execution timeMemoryGrader output
Fetching results...
#Verdict Execution timeMemoryGrader output
Fetching results...
#Verdict Execution timeMemoryGrader output
Fetching results...
#Verdict Execution timeMemoryGrader output
Fetching results...
#Verdict Execution timeMemoryGrader output
Fetching results...
#Verdict Execution timeMemoryGrader output
Fetching results...
#Verdict Execution timeMemoryGrader output
Fetching results...