HDU5727 Necklace
http://acm.hdu.edu.cn/showproblem.php?pid=5727
题意:n个珠子,每个珠子有阴阳两种属性,且阴的一定和阳的紧邻,排成一个环;m行,每行两个数,表示阳性x珠子和y阴性珠子相邻则功能减弱,问功能减弱珠子最少有几个
思路:二分匹配
全排列阴性珠子,因为是环,O((n-1)!);枚举每个阳性珠子,插入i位置,前提是i前后两个阴性珠子都不与阳性珠子有排斥作用;
最后问题变转化成,阳性珠子和位置的最大匹配问题
1 // #pragma comment(linker, "/STACK:102c000000,102c000000") 2 #include <iostream> 3 #include <cstdio> 4 #include <cstring> 5 #include <sstream> 6 #include <string> 7 #include <algorithm> 8 #include <list> 9 #include <map> 10 #include <vector> 11 #include <queue> 12 #include <stack> 13 #include <cmath> 14 #include <cstdlib> 15 // #include <conio.h> 16 using namespace std; 17 #define clc(a,b) memset(a,b,sizeof(a)) 18 #define inf 0x3f3f3f3f 19 #define lson l,mid,rt<<1 20 #define rson mid+1,r,rt<<1|1 21 const int N = 50010; 22 const int M = 1e6+10; 23 const int MOD = 1e9+7; 24 #define LL long long 25 #define LB long double 26 #define mi() (l+r)>>1 27 double const pi = acos(-1); 28 const double eps = 1e-8; 29 void fre() { 30 freopen("in.txt","r",stdin); 31 } 32 // inline int r() { 33 // int x=0,f=1;char ch=getchar(); 34 // while(ch>'9'||ch<'0') {if(ch=='-') f=-1;ch=getchar();} 35 // while(ch>='0'&&ch<='9') { x=x*10+ch-'0';ch=getchar();}return x*f; 36 // } 37 int mp[10][10]; 38 int a[15]; 39 int n,m; 40 int ans; 41 bool vis[15]; 42 int b[15]; 43 vector<int>s[10]; 44 bool dfs(int x){ 45 if(vis[x]) return false; 46 vis[x]=1; 47 for(int i=0;i<(int)s[x].size();i++){ 48 int v=s[x][i]; 49 if(b[v]==-1||dfs(b[v])){ 50 b[v]=x; 51 return true; 52 } 53 } 54 return false; 55 } 56 57 void hungarian(){ 58 clc(b,-1); 59 int tem=0; 60 for(int i=1;i<=n;i++){ 61 clc(vis,0); 62 if(dfs(i)) 63 tem++; 64 } 65 if(tem>ans) ans=tem; 66 } 67 void work(){ 68 for(int i=0;i<n;i++){ 69 a[i]=i+1; 70 } 71 do{ 72 for(int i=0;i<=10;i++) s[i].clear(); 73 for(int i=0;i<n;i++){ 74 int k1=a[i],k2=a[(i-1+n)%n]; 75 for(int j=1;j<=n;j++){ 76 if(!mp[k1][j]&&!mp[k2][j]) s[j].push_back(i); 77 } 78 } 79 hungarian(); 80 }while(next_permutation(a+1,a+n)&&ans!=n); 81 } 82 int main(){ 83 // fre(); 84 while(~scanf("%d%d",&n,&m)){ 85 clc(mp,0); 86 ans=0; 87 for(int i=0;i<m;i++){ 88 int x,y; 89 scanf("%d%d",&x,&y); 90 mp[y][x]=1; 91 } 92 work(); 93 printf("%d\n",n-ans); 94 } 95 return 0; 96 }