Submission #573962

#TimeUsernameProblemLanguageResultExecution timeMemory
573962JovanBBoarding Passes (BOI22_passes)C++17
100 / 100
186 ms48296 KiB
#include <bits/stdc++.h>
using namespace std;

using ll = long long;
using ld = long double;

const int N = 100000;
const int C = 15;

ll dp[N+5];

vector <int> vec[C+1];

ll levo[C+1][N+5];
ll desno[C+1][N+5];
ll plevo[C+1][N+5];
ll pdesno[C+1][N+5];

int main(){
    ios_base::sync_with_stdio(false), cin.tie(0);
    cout.precision(1);
    cout << fixed;

    string s;
    cin >> s;
    int n = s.size();
    for(int i=0; i<n; i++){
        vec[s[i] - 'A'].push_back(i + 1);
    }
    for(int i=0; i<C; i++){
        for(int j=0; j<C; j++){
            if(i == j){
                ll p = 0;
                for(int k=0; k<vec[j].size(); k++){
                    levo[i][vec[j][k]] = p;
                    plevo[i][vec[j][k]] = p*(p+1)/2;
                    p++;
                }
                p = 0;
                for(int k=int(vec[j].size())-1; k>=0; k--){
                    desno[i][vec[j][k]] = p;
                    pdesno[i][vec[j][k]] = p*(p+1)/2;
                    p++;
                }
            }
            else{
                ll tr = 0;
                int d = 0;
                for(int k=0; k<vec[j].size(); k++){
                    while(d < vec[i].size() && vec[i][d] < vec[j][k]){
                        d++;
                    }
                    levo[i][vec[j][k]] = 2*d;
                    tr += 2*d;
                    plevo[i][vec[j][k]] = tr;
                }
                tr = 0, d = int(vec[i].size()) - 1;
                for(int k=int(vec[j].size())-1; k>=0; k--){
                    while(d >= 0 && vec[i][d] > vec[j][k]){
                        d--;
                    }
                    desno[i][vec[j][k]] = 2*(int(vec[i].size()) - d - 1);
                    tr += 2*(int(vec[i].size()) - d - 1);
                    pdesno[i][vec[j][k]] = tr;
                }
            }
        }
    }
    for(int mask=1; mask<(1<<C); mask++){
        dp[mask] = 1e18;
        bool em = 0;
        for(int i=0; i<C; i++){
            if((mask & (1 << i)) && vec[i].size() == 0){
                dp[mask] = dp[mask ^ (1 << i)];
                em = 1;
                break;
            }
        }
        if(em) continue;
        for(int i=0; i<C; i++){
            if(!((1 << i) & mask)) continue;
            int sub = mask ^ (1 << i);
            int l = 0, r = vec[i].size() - 1, d = -1;
            while(l <= r){
                int mid = (l+r)/2;
                ll ul = 0, ud = 0;
                for(int j=0; j<C; j++){
                    if(mask & (1 << j)){
                        ul += levo[j][vec[i][mid]];
                        ud += desno[j][vec[i][mid]];
                    }
                }
                if(ul <= ud){
                    d = mid;
                    l = mid + 1;
                }
                else r = mid - 1;
            }
            ll tot = 0;
            for(int j=0; j<C; j++){
                if(mask & (1 << j)){
                    if(d >= 0) tot += plevo[j][vec[i][d]];
                    if(d < int(vec[i].size()) - 1) tot += pdesno[j][vec[i][d+1]];
                }
            }
            dp[mask] = min(dp[mask], dp[sub] + tot);
        }
    }
    ll k = dp[(1<<C)-1];
    if(k%2 == 0) cout << k/2 << "\n";
    else cout << 1.0*k/2 << "\n";
    return 0;
}

Compilation message (stderr)

passes.cpp: In function 'int main()':
passes.cpp:34:31: warning: comparison of integer expressions of different signedness: 'int' and 'std::vector<int>::size_type' {aka 'long unsigned int'} [-Wsign-compare]
   34 |                 for(int k=0; k<vec[j].size(); k++){
      |                              ~^~~~~~~~~~~~~~
passes.cpp:49:31: warning: comparison of integer expressions of different signedness: 'int' and 'std::vector<int>::size_type' {aka 'long unsigned int'} [-Wsign-compare]
   49 |                 for(int k=0; k<vec[j].size(); k++){
      |                              ~^~~~~~~~~~~~~~
passes.cpp:50:29: warning: comparison of integer expressions of different signedness: 'int' and 'std::vector<int>::size_type' {aka 'long unsigned int'} [-Wsign-compare]
   50 |                     while(d < vec[i].size() && vec[i][d] < vec[j][k]){
      |                           ~~^~~~~~~~~~~~~~~
#Verdict Execution timeMemoryGrader output
Fetching results...
#Verdict Execution timeMemoryGrader output
Fetching results...
#Verdict Execution timeMemoryGrader output
Fetching results...
#Verdict Execution timeMemoryGrader output
Fetching results...