版权声明:虽然本蒟蒻很菜,但各位dalao转载请注明出处谢谢。 https://blog.csdn.net/xuxiayang/article/details/90084625
给定一张 无向图,求环个数
设 表示经过了 的这些点,终点为 ,起点为 的方案数
边界:
转移显然:
当 的第 位不为1时,即第 个点没有走过时, ,否则不转移
如果 ,则说明出现了环,
最后答案要排除无向图的干扰以及边界带来的计算误差,
记得开 ,然后空集不转移,这样就 了
时间复杂度最坏 ,空集不转移就过掉了
#include<cstdio>
#define lb(x) (x&-x)
using namespace std;int n,m,t;
bool a[19][19];
long long ans,f[600001][19];
signed main()
{
scanf("%d%d",&n,&m);
t=1<<n;
for(register int i=1,x,y;i<=m;i++) scanf("%d%d",&x,&y),a[--x][--y]=a[y][x]=true;
for(register int i=0;i<n;i++) f[1<<i][i]=1;
for(register int i=1;i<t;i++)
for(register int j=0;j<n;j++)
if(f[i][j])//有值才转移
for(register int k=0;k<n;k++)
if(a[j][k]&&lb(i)<=(1<<k))
if(i>>k&1)
{
if(1<<k==lb(i)) ans+=f[i][j];
}
else f[i|1<<k][k]+=f[i][j];
printf("%lld",(ans-m)/2);
}