zoukankan      html  css  js  c++  java
  • 【NOI2008T1】假面舞会-DFS环处理+最大公因数

    测试地址:假面舞会

    做法:这题看上去就是找环然后求最大公因数,然后下一步就不会做了,看了题解就跪了......主要这个处理方法太神奇了。

    首先建图肯定不能按照原来的图建,因为需要枚举起点来走,会TLE,所以我们对于原图a->b这条边,连一条a->b边权为1,再连一条b->a边权为-1。如果图中有非零环,那么最大的答案就是所有非零环长的最大公因数,最小答案就是所有非零环长的最小的大于2的公因数。如果图中没有非零环,就统计每个连通块的最长链长,这个长度加上1就是这个连通块的最大答案,累加每个连通块的最大答案就是整体的最大答案,最小答案就是3。如果最大答案小于3则无解。

    以下是本人代码:

    #include <cstdio>
    #include <cstdlib>
    #include <cstring>
    #include <iostream>
    #include <algorithm>
    #define inf 1000000000
    using namespace std;
    int n,m,cnt[100010],first[100010]={0},tot=0,maxn,minn;
    int len[100010]={0},ans1,ans2;
    struct edge {int v,d,next;} e[2000010];
    bool vis[100010]={0},flag=0;
    
    int gcd(int a,int b)
    {
      return b!=0?gcd(b,a%b):a;
    }
    
    void insert(int a,int b,int d)
    {
      e[++tot].v=b,e[tot].d=d,e[tot].next=first[a],first[a]=tot;
    }
    
    void dfs(int v)
    {
      vis[v]=1;
      maxn=max(maxn,cnt[v]);
      minn=min(minn,cnt[v]);
      for(int i=first[v];i;i=e[i].next)
      {
        if (!vis[e[i].v])
    	{
    	  cnt[e[i].v]=cnt[v]+e[i].d;
    	  dfs(e[i].v);
    	}
        else if (cnt[v]+e[i].d-cnt[e[i].v]!=0)
    	{
    	  flag=1;
    	  if (ans1==0) ans1=abs(cnt[v]+e[i].d-cnt[e[i].v]);
    	  else ans1=gcd(ans1,abs(cnt[v]+e[i].d-cnt[e[i].v]));
    	}
      }
    }
    
    int main()
    {
      scanf("%d%d",&n,&m);
      for(int i=1,a,b;i<=m;i++)
      {
        scanf("%d%d",&a,&b);
    	insert(a,b,1),insert(b,a,-1);
      }
      
      ans1=0;
      for(int i=1;i<=n;i++)
      if (!vis[i])
      {
        cnt[i]=0;
    	maxn=-inf,minn=inf;
    	dfs(i);
    	if (!flag) ans1+=maxn-minn+1;
      }
      
      ans1=abs(ans1);
      if (ans1<3) ans1=-1,ans2=-1;
      else if (!flag) ans2=3;
      else
      {
        for(int i=3;i<=ans1;i++)
    	  if (ans1%i==0) {ans2=i;break;}
      }
      
      printf("%d %d",ans1,ans2);
      
      return 0;
    }
    


  • 相关阅读:
    积水路面Wet Road Materials 2.3
    门控时钟问题
    饮料机问题
    Codeforces Round #340 (Div. 2) E. XOR and Favorite Number (莫队)
    Educational Codeforces Round 82 (Rated for Div. 2)部分题解
    Educational Codeforces Round 86 (Rated for Div. 2)部分题解
    Grakn Forces 2020部分题解
    2020 年百度之星·程序设计大赛
    POJ Nearest Common Ancestors (RMQ+树上dfs序求LCA)
    算法竞赛进阶指南 聚会 (LCA)
  • 原文地址:https://www.cnblogs.com/Maxwei-wzj/p/9793753.html
Copyright © 2011-2022 走看看