【polya】He's Circles

1 篇文章 0 订阅

题♂面

思路

polya模版题。

what is polya?

我们可以发现,一个循环节之间的“不变元素”可以互相交换从而不影响整体,所以我们可以设Ci为置换群i的循环节个数。

         例如(1 2 3 4 5

               3 5 1 4 2)

         的循环节就为:1和3循环1->3->1……

                             2和5循环2->5->2……

                             4和它自身循环4->4->4……

       那么循环节数就为3

       再回来看现在这个题目,我们可以抽象地把Ci替换掉Di

       那么Di=p^C(i) (p为总共的字母数)

       相同循环节中的元素可以互相置换,所以Di=p^C(i)

       polya公式为1/|G|(p^C(1)+p^C(2)+……+p^C(s))

       以4为例,则1/|G|=1/4

      C(1):循环节为(1)(2)(3)(4),所以C(1)=4

      C(2):循环节为(4 3 2 1),所以C(2)=1

      C(3):循环节为(1 3)(2 4),所以C(3)=2

      C(4):循环节为(1 2 3 4),所以C(4)=1

      那么答案就为1/4(2^4+2^1+2^2+2^1)=6

      这里的C相对于上面的D来说要简单,记得XJR学长给我讲过环的判定,直接任选一个没有选过的点,从这个点开始映射,走过的点标上1,等到再走到标上1时,结束,统计数加1

代码

#include<iostream>
#include<cstdio>
#include<cstring>
using namespace std;
const int mod=1e9+7,maxn=2e5+77;
int b[maxn],n,s=0,ass=0;
bool f[maxn];
void fin(int t)
{
    int i=t;
    f[i]=1;
    while(!f[b[i]])
    {
        i=b[i]; f[i]=1;
    }
    return;
}
int polya()
{
    int t=0;
    memset(f,0,sizeof(f));
    for(int i=1; i<=n; i++) if(!f[b[i]]) fin(i),t++;
    return t;
}
void P(int x,int t)
{
    if(!x) return;
    if(x%2==0)
    {
        P(x/2,t); 
        s=(s*s)%mod;
    }else
    {
        P(x/2,t); 
        s=(s*s)%mod; s=s*t%mod;
    }
    return;
}
int main()
{
    scanf("%d",&n);
    for(int i=0; i<n; i++)
    {
        for(int j=1; j<=n; j++) b[j]=(j+i)%n+1;
        s=1;
        P(polya(),2);
        ass+=s;
    }
    printf("%d",ass/n);
}
  • 1
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值