Codeforces Round #533 (Div. 2)E. Helping Hiasat_求最大独立子集转换求最大团
题目链接:E. Helping Hiasat
题解:把夹在同一段1里面的人互相连边,然后问题就转换为求最大独立子集的大小,最大独立子集大小等于补图的最大团。最大图不会的可以看这篇博客,我也是看这个的
#include<bits/stdc++.h> #include<iostream> #include<string> #include<cstring> #include<algorithm> #define pb push_back #define ll long long #define PI 3.14159265 #define ls l,m,rt<<1 #define rs m+1,r,rt<<1|1 #define eps 1e-7 using namespace std; const int N=50; const int mod=1e9+7; int n,m; int g[N][N]; map<string ,int >mp; vector<int>ve; int ret=0; int cnt[N],vis[N],ans; bool dfs(int u,int d) { for(int i=u+1;i<m;i++) { if(d+cnt[i]<=ans)return 0; if(g[u][i]) { int j; for(j=0;j<d;j++)if(!g[i][vis[j]])break; if(j==d) { vis[d]=i; if(dfs(i,d+1))return 1; } } } if(d>ans) { ans=d;return 1; } return false; } int maxclique() { ans=0; for(int i=m-1;i>=0;i--) { vis[0]=i; dfs(i,1); cnt[i]=ans; } return ans; } int main() { std::ios::sync_with_stdio(false);cin.tie(0);cout.tie(0); cin>>n>>m; for(int i=0;i<=n;i++) { int op; if(i!=n)cin>>op; else op=1; if(op==1) { for(int j=0;j<ve.size();j++) { for(int k=j+1;k<ve.size();k++) { g[ve[j]][ve[k]]=1,g[ve[k]][ve[j]]=1; //cout<<"SSS"<<endl; } } ve.clear(); } else { string s;cin>>s; if(mp.count(s)==0)mp[s]=ret++; ve.pb(mp[s]); } } for(int i=0;i<m;i++) for(int j=0;j<m;j++)g[i][j]^=1; cout<<maxclique()<<endl; }