题解 特殊字符串
处理 \(tran[i][j]\) 表示在 \(i\) 后面接 \(j\) 的贡献,然后按题意DP
Code:
#include <bits/stdc++.h>
using namespace std;
#define INF 0x3f3f3f3f
#define N 100010
#define ll long long
//#define int long long
int n, m;
ll tran[30][30];
char s[N], t1[10], t2[10];
namespace force{
int tot;
ll ans;
char tem[N];
ll check() {ll ans=0; for (int i=2; i<=tot; ++i) ans+=tran[tem[i-1]-'a'][tem[i]-'a']; return ans;}
void dfs(int u) {
if (u>n) {
ans=max(ans, check());
return ;
}
dfs(u+1);
tem[++tot]=s[u];
dfs(u+1);
--tot;
}
void solve() {
dfs(1);
printf("%lld\n", ans);
exit(0);
}
}
namespace task1{
ll dp[N][30], ans;
void solve() {
for (int i=0; i<26; ++i) dp[1][i]=-1e16;
dp[1][s[1]-'a']=0;
for (int i=2; i<=n; ++i) {
for (int j=0; j<26; ++j) {
if (j==s[i]-'a') for (int k=0; k<26; ++k) dp[i][j]=max(dp[i][j], dp[i-1][k]+tran[k][j]);
else dp[i][j]=dp[i-1][j];
}
}
for (int i=0; i<26; ++i) ans=max(ans, dp[n][i]);
printf("%lld\n", ans);
exit(0);
}
}
signed main()
{
freopen("shiki.in", "r", stdin);
freopen("shiki.out", "w", stdout);
scanf("%d%s%d", &n, s+1, &m);
for (int i=1,k; i<=m; ++i) {
scanf("%s%s%d", t1, t2, &k);
tran[(*t1)-'a'][(*t2)-'a']+=k;
}
// force::solve();
task1::solve();
return 0;
}