容易发现有了交换相邻字符的操作后,只要字符串所含有的字符种类和数量相同其就是等价的。这样的状态只有n^3级别,将其抽象成点子串变换抽象成边后就是求最长路径了,缩点dp解决。

  码量巨大,不是很明白要怎样才能用3k写完。

#include<iostream>
#include<cstdio>
#include<cmath>
#include<cstdlib>
#include<cstring>
#include<algorithm>
#include<vector>
using namespace std;
int read()
{int x=0,f=1;char c=getchar();while (c<'0'||c>'9') {if (c=='-') f=-1;c=getchar();}while (c>='0'&&c<='9') x=(x<<1)+(x<<3)+(c^48),c=getchar();return x*f;
}
#define N 55
#define P 100000000000000000LL
unsigned long long C[N][N];
int n,m,p[N*N*N],t=0,tmp[20];
int dfn[N*N*N],low[N*N*N],stk[N*N*N],SET[N*N*N],top=0,cnt=0;
bool flag[N*N*N];
char s[N],s2[N];
vector<int> ele[N*N*N];
struct magic{int n,a,b,c,x,y,z;}a[N<<1];
struct data{int to,nxt;}edge[N*N*N*N];
struct biginteger
{unsigned long long x,y;bool operator <(const biginteger&a) const{return x==a.x?y<a.y:x<a.x;}bool operator >(const biginteger&a) const{return x==a.x?y>a.y:x>a.x;}biginteger operator +(const biginteger&a) const{biginteger v=(biginteger){x,y};v.x+=a.x;v.y+=a.y;if (v.y>=P) v.x++,v.y-=P;return v;}biginteger operator *(const unsigned long long&a) const{unsigned long long v[40]={0};int n=0;biginteger tmp=(biginteger){x,y};while (tmp.y) v[++n]=tmp.y%10,tmp.y/=10;    if (tmp.x){n=17;while (tmp.x) v[++n]=tmp.x%10,tmp.x/=10;}for (int i=1;i<=n;i++) v[i]=v[i]*a;for (int i=1;i<=n;i++)v[i+1]+=v[i]/10,v[i]%=10;while (v[n+1]) n++,v[n+1]+=v[n]/10,v[n]%=10;for (int i=17;i>=1;i--) tmp.y=tmp.y*10+v[i];for (int i=n;i>=18;i--) tmp.x=tmp.x*10+v[i];return tmp;}
}value[N*N*N],V[N*N*N],f[N*N*N];
int trans(int x,int y,int z){return x*(n+1)*(n+1)+y*(n+1)+z+1;}
void addedge(int x,int y){t++;edge[t].to=y,edge[t].nxt=p[x],p[x]=t;}
void tarjan(int k)
{dfn[k]=low[k]=++cnt;flag[k]=1;stk[++top]=k;for (int i=p[k];i;i=edge[i].nxt)if (!dfn[edge[i].to]) tarjan(edge[i].to),low[k]=min(low[k],low[edge[i].to]);else if (flag[edge[i].to]) low[k]=min(low[k],dfn[edge[i].to]);if (dfn[k]==low[k]){t++;while (stk[top]!=k){SET[stk[top]]=t;ele[t].push_back(stk[top]);V[t]=V[t]+value[stk[top]];flag[stk[top]]=0;top--;}SET[k]=t;ele[t].push_back(k);V[t]=V[t]+value[k];flag[k]=0;top--;}
}
namespace newgraph
{int n,t=0,p[N*N*N]={0},degree[N*N*N],q[N*N*N];struct data{int to,nxt;}edge[N*N*N*N];void addedge(int x,int y){t++;edge[t].to=y,edge[t].nxt=p[x],p[x]=t;}void topsort(){int head=0,tail=0;for (int i=1;i<=n;i++) if (!degree[i]) q[++tail]=i;while (tail<n){int x=q[++head];for (int i=p[x];i;i=edge[i].nxt){degree[edge[i].to]--;if (!degree[edge[i].to]) q[++tail]=edge[i].to;}}}void solve(){topsort();for (int i=n;i>=1;i--){for (int j=p[q[i]];j;j=edge[j].nxt)f[q[i]]=max(f[q[i]],f[edge[j].to]);f[q[i]]=f[q[i]]+V[q[i]];}}
}
void rebuild()
{memset(flag,0,sizeof(flag));for (int i=1;i<=t;i++){for (int j=0;j<ele[i].size();j++)for (int k=p[ele[i][j]];k;k=edge[k].nxt)if (!flag[edge[k].to]&&SET[edge[k].to]!=i){flag[edge[k].to]=1;newgraph::addedge(i,SET[edge[k].to]);newgraph::degree[SET[edge[k].to]]++;}for (int j=0;j<ele[i].size();j++)for (int k=p[ele[i][j]];k;k=edge[k].nxt)flag[edge[k].to]=0;}newgraph::n=t;
}
int main()
{n=read(),m=read();for (int i=1;i<=m;i++){scanf("%s",s+1);scanf("%s",s2+1);a[i].n=strlen(s+1);for (int j=1;j<=a[i].n;j++)if (s[j]=='A') a[i].a++;else if (s[j]=='B') a[i].b++;else if (s[j]=='C') a[i].c++;for (int j=1;j<=a[i].n;j++)if (s2[j]=='A') a[i].x++;else if (s2[j]=='B') a[i].y++;else if (s2[j]=='C') a[i].z++;if (a[i].a==a[i].x&&a[i].b==a[i].y&&a[i].c==a[i].z) a[i].a=a[i].b=a[i].c=n+1;}C[0][0]=1;for (int i=1;i<=n;i++){C[i][0]=C[i][i]=1;for (int j=1;j<i;j++)C[i][j]=C[i-1][j-1]+C[i-1][j];}for (int i=0;i<=n;i++)for (int j=0;j<=n-i;j++)for (int k=0;k<=n-i-j;k++){value[trans(i,j,k)]=(biginteger){0,C[n][i]};value[trans(i,j,k)]=value[trans(i,j,k)]*C[n-i][j];value[trans(i,j,k)]=value[trans(i,j,k)]*C[n-i-j][k];for (int x=1;x<=m;x++)if (i>=a[x].a&&j>=a[x].b&&k>=a[x].c&&n-i-j-k>=a[x].n-a[x].a-a[x].b-a[x].c)addedge(trans(i,j,k),trans(i-a[x].a+a[x].x,j-a[x].b+a[x].y,k-a[x].c+a[x].z));}t=0;for (int i=0;i<=n;i++)for (int j=0;j<=n-i;j++)for (int k=0;k<=n-i-j;k++)if (!dfn[trans(i,j,k)]) tarjan(trans(i,j,k));rebuild();newgraph::solve();biginteger ans=(biginteger){0,0};for (int i=1;i<=t;i++) ans=max(ans,f[i]);if (ans.x){cout<<ans.x;int x=0;while (ans.y) tmp[++x]=ans.y%10,ans.y/=10;for (int i=17;i>=1;i--) cout<<tmp[i];}else cout<<ans.y;return 0;
}

转载于:https://www.cnblogs.com/Gloid/p/9613467.html

#35 string(缩点+动态规划)相关推荐

  1. ACM学习历程—HDU2476 String painter(动态规划)

    http://acm.hdu.edu.cn/showproblem.php?pid=2476 题目大意是给定一个起始串和一个目标串,然后每次可以将某一段区间染成一种字符,问从起始串到目标串最少需要染多 ...

  2. NYOJ练习题 Splits the string (简单动态规划)

    Splits the string 时间限制:1000 ms  |  内存限制:65535 KB 描述 Hrdv is interested in a string,especially the pa ...

  3. 学用 ASP.Net 之 字符串 (2): string.Format

    一般应用与左右对齐: protected void Button1_Click(object sender, EventArgs e) {TextBox1.TextMode = TextBoxMode ...

  4. C风格字符串和C++ string 对象赋值操作的性能比较

    <<C++ Primer>> 第四版 Exercise Section 4.3.1 部分Exercise 4.2.9 习题如下: 在自己本机执行如下程序,记录程序执行时间: 1 ...

  5. 【LeetCode】字符串 string(共112题)

    [3]Longest Substring Without Repeating Characters (2019年1月22日,复习) [5]Longest Palindromic Substring ( ...

  6. 牛人总结python中string模块各属性以及函数的用法,果断转了,好东西

    原文链接:http://blog.chinaunix.net/uid-25992400-id-3283846.html 任何语言都离不开字符,那就会涉及对字符的操作,尤其是脚本语言更是频繁,不管是生产 ...

  7. string.Format出现异常输入的字符串格式有误的解决方法

    今天在做项目时,碰到一个很奇怪的问题,我使用string.Format居然报"输入的字符串格式有误"的错误,我调了很久,还是不对,不明白错在哪里,后来还是google了一下,原来我 ...

  8. String, StringBuffer, StringBuilder之间的区别

    String与StringBuffer/StringBuilder之间的主要区别 1.String对象不可变, 如果修改会重新创建一个对象, 然后把值保存进去. StringBuffer/String ...

  9. python isalpha函数用法_python中string模块各属性以及函数的用法

    任何语言都离不开字符,那就会涉及对字符的操作,尤其是脚本语言更是频繁,不管是生产环境还是面试考验都要面对字符串的操作. python的字符串操作通过2部分的方法函数基本上就可以解决所有的字符串操作需求 ...

最新文章

  1. 企业并不怕尝新 业务变革的技术们
  2. MyBatis 流式查询
  3. linux2.6内核compat_ioctl函数
  4. transpose公式_EXCEL转置你是用公式还是选择性粘贴?
  5. 监控系统简介:使用 Prometheus 与 Grafana
  6. memmove 对同一个指针不操作
  7. ZZULIOJ 1061:顺序输出各位数字
  8. 算数编码与哈夫曼编码的比较【转载】
  9. [No0000FD]C# 正则表达式
  10. NFS挂载及写入故障
  11. inotifywait监听php,inotifywait 是一个可以实时监控文件变动的工具
  12. magento模板中XML与phtml关系 [四]
  13. 嵌入式linux地图,基于嵌入式Linux的MapInfo格式地图显示
  14. FileZilla Server连接服务器失败
  15. JavaWeb之HttpSession
  16. 一款阿里的知识管理工具
  17. codeforces-379C. New Year Ratings Change
  18. php 漏洞_十大PHP安全漏洞
  19. 【CS231n】斯坦福大学李飞飞视觉识别课程笔记(十九):卷积神经网络笔记(下)
  20. 浅谈数据中心综合布线运维管理方式发展史

热门文章

  1. 建筑电气工程设计常用图形和文字符号_建筑水电图纸看不懂?10年老师傅教你看图技巧,分分钟安排...
  2. php写抢票脚本,火车票抢票python代码公开揭秘!
  3. 一、AJAX学习笔记——原生AJAX (ajax简介、XML简介、ajax优缺点、ajax的使用)
  4. 一、数据预处理——数据归一化 数据标准化
  5. LeetCode 2162. 设置时间的最少代价(枚举)
  6. LeetCode 2063. 所有子字符串中的元音(数学)
  7. LeetCode 1637. 两点之间不包含任何点的最宽垂直面积
  8. LeetCode 930. 和相同的二元子数组(哈希+前缀和)
  9. LeetCode 1306. 跳跃游戏 III(广度优先搜索BFS)
  10. LeetCode 1222. 可以攻击国王的皇后(set)