Submission #1370381

#TimeUsernameProblemLanguageResultExecution timeMemory
1370381pirmyratgCopy and Paste 3 (JOI22_copypaste3)C++20
100 / 100
1776 ms456568 KiB
#include "bits/stdc++.h"
using namespace std;
#define mod 1000000007
#define ll long long
#define ff first
#define ss second
#define pb push_back
#define N 24
#define maxn 2510
#define INF (ll)1e18

ll n,a,b,c;
ll h[maxn],pw[maxn];
string s;
vector<ll> occ[maxn*maxn];
ll dp[maxn*maxn],pt[maxn*maxn];
ll nxt[maxn][maxn],hs[maxn][maxn];
unordered_map<ll,ll> mp;

ll get(ll i,ll j){
	return hs[i][j];
}

void solve(){
	cin>>n>>s>>a>>b>>c;
	s='#'+s;
	pw[0]=1;
	for(ll i=1; i<=n; i++){
		h[i]=h[i-1]*29+(s[i]-'a'+1);
		pw[i]=pw[i-1]*29;
	}
	vector<ll> v;
	for(ll i=1; i<=n; i++){
		for(ll j=i; j<=n; j++){
			hs[i][j]=h[j]-h[i-1]*pw[j-i+1];
			v.pb(hs[i][j]);
		}
	}
	///v.erase(unique(v.begin(), v.end()), v.end());
	///sort(v.begin(), v.end());
	for(ll i=0; i<v.size(); i++){
		if(mp[v[i]]==0)mp[v[i]]=i+1;
	}
	for(ll i=1; i<=n; i++){
		for(ll j=i; j<=n; j++)hs[i][j]=mp[hs[i][j]];
	}
	for(ll i=n; i>0; i--){

			////cout << "------------" << endl;
		for(ll j=i; j<=n; j++){
			ll cur=hs[i][j];
			occ[cur].pb(i);
			/**cout << "hash " << i << " " << p << endl;
            cout << "occurrences: ";
            for (int ds : occ[cur_hs])
                cout << ds << " ";
            cout << endl;*/
			if(occ[cur].size()==1){
				dp[cur]=dp[hs[i+1][j]]+a;
				nxt[j-i+1][j]=n+1;
				pt[cur]=-1;
			}
			else{
				dp[cur]=min(dp[cur],dp[hs[i+1][j]]+a);
				if(pt[cur]==-1)pt[cur]++;
				while(occ[cur][pt[cur]]>j)pt[cur]++;
				pt[cur]--;
				///cout << i << endl;
				if(pt[cur]==-1)nxt[j-i+1][j]=n+1;
				else nxt[j-i+1][j]=occ[cur][pt[cur]]+(j-i);
			///cout << "step " << i << " " << p << " " << nxt[p - i + 1][p] << endl;
			}
		}



		for(ll j=i; j<=n; j++){
			ll cur=get(i,j),len=j-i+1;
			ll cost=dp[cur]+b+c;
			if(occ[get(i,j)].size()<2)break;
			ll pos=j,pp=(ll)occ[cur].size()-1;
			///dp[get_hash(i, k)] = min(dp[get_hash(i, k)], cos);
			//cout << "-------------------" << endl;
			///cout << i << " " << k << endl;
			while(pos<=n){
				//cout << pos << " " << cost << endl;
				ll to=nxt[len][pos];
				if(to>n)break;
				cost=cost+(to-pos-len)*a;
				cost=cost+c;
				///cout << "stop " << occ[clip_hash][pt] << endl;
				///cost = cost + (occ[clip_hash][pt] - pos) * a;
				///cost = cost + c;
				pos=to;
				dp[hs[i][pos]]=min(dp[hs[i][pos]],cost);

				/**int to = pos + clip_len - 1;

                if (to > n)
                {
                    break;
                }

                if (get_hash(pos, to) == clip_hash)
                {

                    cost = cost + c;
                    pos = pos + clip_len;
                    hs_dp[get_hash(i, to)] = min(hs_dp[get_hash(i, to)], cost);
                }
                else
                {
                    pos ++;
                    cost += a;
                }*/
			}
		}
		for(ll j=i; j<=n; j++){
			dp[hs[i][j]]=min(dp[hs[i][j]],dp[hs[i][j-1]]+a);
		}
	}

	/**for (int i = 1; i <= n; i ++, cout << endl)
        for (int j = i; j <= n; j ++)
            cout << hs_dp[get_hash(i, j)] << " ";*/

	cout<<dp[hs[1][n]]<<'\n';
}
 
int main(){
	// freopen("in.txt","w",stdout);
	// freopen("out.txt","r",stdin);
	ios_base::sync_with_stdio(0); cin.tie(0);
	ll t=1;
	// cin>>t;
	while(t--) solve();
}
#Result Execution timeMemoryGrader output
Fetching results...
#Result Execution timeMemoryGrader output
Fetching results...
#Result Execution timeMemoryGrader output
Fetching results...
#Result Execution timeMemoryGrader output
Fetching results...
#Result Execution timeMemoryGrader output
Fetching results...
#Result Execution timeMemoryGrader output
Fetching results...