zoukankan      html  css  js  c++  java
  • 【简单计数知识2】JZOJ6405. 【NOIP2019模拟11.04】c

    Description

    在这里插入图片描述
    在这里插入图片描述
    n<=1e6,m<1e9+7n<=1e6,m<1e9+7

    Solution

    • 刚开始看到矩阵求逆后发现连裸的矩阵求逆我都不会(其实我去年应该是学过的。。。),只会一发n6的暴力对n2个点进行高斯消元。
    • 实际上,矩阵求逆有一种很好做的n3高斯消元。
    • 对于矩阵AA,将它变为单元矩阵II,同时根据AA的操作,同步地操作一个II,因为矩阵的操作是互逆的,所以II在经过相同的操作后就变成了AA^-
    • 考虑对于这个Pascal矩阵做同样的操作。
    • 注意到这个矩阵已经是一个三角形了,并且对于同一列,它们的分母都是一样的jmj^m,所以在消元的时候可以忽略这个。那么只需要将这个矩阵消成一个对角线的1就好了。
    • 然后因为这个矩阵P(i,j)=[i>=j]CijP(i,j)=[i>=j]C_i^j,这个其实是二项式反演的基本式子,它的逆矩阵就是二项式反演的容斥系数P(i,j)=[i>=j](1)i+jCijP(i,j)=[i>=j](-1)^{i+j}C_i^j.
    • 然后再把jmj^m乘上去就好了。
    • 最后计算每一列的平方和。即i=0n(Cni)2sum_{i=0}^n (C_n^i)^2
    • 结论i=0n(Cni)2=C2nnsum_{i=0}^n (C_n^i)^2=C_{2n}^n

    小证明

    • 简单的理解成CniCnniC_n^i*C_n^{n-i}即将2n个数分成两半,前一半选i个,后一半选n-i个,因为枚举了i,所以相当于是2n里面选n个。
    #include<cstdio>
    #include<cmath>
    #include<cstring>
    #include<algorithm>
    #define maxm 2000005
    #define ll long long 
    #define mo 1000000007
    using namespace std;
    
    int n,m,i,j,k;
    ll fct[maxm],ift[maxm],ans;
    
    ll ksm(ll x,ll y){
    	ll s=1;
    	for(;y;y/=2,x=x*x%mo) if (y&1)
    		s=s*x%mo;
    	return s;
    }
    
    ll C(int n,int m){return fct[n]*ift[m]%mo*ift[n-m]%mo;}
    
    int main(){
    	freopen("c.in","r",stdin);
    	freopen("c.out","w",stdout);
    	scanf("%d%d",&n,&m);
    	fct[0]=fct[1]=1;for(i=2;i<maxm;i++) fct[i]=fct[i-1]*i%mo;
    	ift[maxm-1]=ksm(fct[maxm-1],mo-2);
    	for(i=maxm-2;i>=0;i--) ift[i]=ift[i+1]*(i+1)%mo;
    	for(i=1;i<=n;i++) ans+=ksm(i,2*m)*(C(2*i,i)-1)%mo;
    	printf("%lld",ans%mo);
    }
    
  • 相关阅读:
    react萌新的读书笔记(一)
    python 读取目录下的文件
    scrapy爬虫入门
    iPad和iPhone如何保护自己的隐私?
    郭盛华动真格了!新公司获百亿融资,网友:还招人不
    僵尸网络瞄准Linux服务器
    中美黑客谁更强?揭秘郭盛华与凯文的传奇故事
    VMware新致命漏洞,黑客可远程控制你的系统
    中国两大网络守护神,为祖国默默付出着,向他们致敬!
    Web应用程序已成为黑客的首要目标
  • 原文地址:https://www.cnblogs.com/DeepThinking/p/13090916.html
Copyright © 2011-2022 走看看