zoukankan      html  css  js  c++  java
  • BZOJ3513: [MUTC2013]idiots

    Description

    给定n个长度分别为a_i的木棒,问随机选择3个木棒能够拼成三角形的概率。

    Input

    第一行T(T<=100),表示数据组数。
    接下来若干行描述T组数据,每组数据第一行是n,接下来一行有n个数表示a_i。

    Output

    T行,每行一个整数,四舍五入保留7位小数。

    Sample Input

    2
    4
    1 3 3 4
    4
    2 3 3 4

    Sample Output

    0.5000000
    1.0000000

    HINT

    T<=20


    N<=100000

    Source

    第一道FFT的题。
    BZOJ上有一个条件没说:0<=a_i<=100000。
    那么我们可以设f[i]为用两个木棒组成长度为i的方案数。
    我们发现这个可用卷积求,于是这道题就做完了。
    #include<cstdio>
    #include<cctype>
    #include<queue>
    #include<cmath>
    #include<cstring>
    #include<algorithm>
    #define rep(i,s,t) for(int i=s;i<=t;i++)
    #define dwn(i,s,t) for(int i=s;i>=t;i--)
    #define ren for(int i=first[x];i!=-1;i=next[i])
    using namespace std;
    inline int read() {
        int x=0,f=1;char c=getchar();
        for(;!isdigit(c);c=getchar()) if(c=='-') f=-1;
        for(;isdigit(c);c=getchar()) x=x*10+c-'0';
        return x*f;
    }
    const int maxn=300010;
    const double PI=acos(-1.0);
    typedef long long ll;
    struct FFT {
        struct cox {
            double r,i;
            cox(double _r=0.0,double _i=0.0) {r=_r;i=_i;}
            cox operator + (const cox& b) const {return cox(r+b.r,i+b.i);}
            cox operator - (const cox& b) const {return cox(r-b.r,i-b.i);}
            cox operator * (const cox& b) const {return cox(r*b.r-i*b.i,r*b.i+i*b.r);}
        }f[maxn];
        int len;
        void init(int* A,int L,int Len) {
            len=L;rep(i,0,Len-1) f[i]=cox(A[Len-i-1],0);rep(i,Len,L-1) f[i]=cox(0,0);
        }
        void cal(int tp) {
            int j=len>>1;
            rep(i,1,len-2) {
                if(i<j) swap(f[i],f[j]);int k=len>>1;
                while(j>=k) j-=k,k>>=1;j+=k;
            }
            double lm=-2*tp*PI;
            for(int i=2;i<=len;i<<=1) {
                cox wn(cos(lm/i),sin(lm/i));
                for(int j=0;j<len;j+=i) {
                    cox w(1,0);
                    for(int k=j;k<j+(i>>1);k++) {
                        cox u=f[k],v=w*f[k+(i>>1)];
                        f[k]=u+v;f[k+(i>>1)]=u-v;w=w*wn;
                    }
                }
            }
            if(tp<0) rep(i,0,len-1) f[i].r/=len;
        }
    };
    void mul(int* A,int* B,int L1,int L2,int& L,ll* ans) {
        L=1;while(L<L1<<1||L<L2<<1) L<<=1;
        static FFT a,b;a.init(A,L,L1);b.init(B,L,L2);
        a.cal(1);b.cal(1);rep(i,0,L-1) a.f[i]=a.f[i]*b.f[i];
        a.cal(-1);rep(i,0,L-1) ans[i]=ll(a.f[i].r+0.5);
    }
    int A[maxn];
    ll ans[maxn],sum[maxn];
    int main() {
        int T=read();
        while(T--) {
            memset(A,0,sizeof(A));
            int n=read(),v,L1=0,L;
            rep(i,1,n) A[v=read()]++,L1=max(L1,v+1);A[0]=0;
            mul(A,A,L1,L1,L,ans);
            while(L>L1+L1-1&&!ans[L-1]) L--;
            dwn(i,L-1,0) sum[L-1-i]=ans[i];
            rep(i,1,L-1) sum[i]=(sum[i]-(i&1?0:A[i>>1]))/2;
            ll res=0,tmp=0,all=0;
            dwn(i,L-1,1) tmp+=A[i],res+=tmp*sum[i];
            rep(i,1,n) all+=(ll)(n-i)*(n-i-1)/2;
            printf("%.7lf
    ",1.0-(double)res/all);
        }
        return 0;
    }
    View Code
  • 相关阅读:
    http和https
    openstack
    openstack安全问题
    openstack优势
    java多线程实现方式
    python多进程实现的几种方式
    Java 在提取url 生成图片以及正则表达式
    idea 生成 可执行文件
    dw cs6 支持高分辨率
    svchost.exe 大量占用的问题
  • 原文地址:https://www.cnblogs.com/wzj-is-a-juruo/p/4695787.html
Copyright © 2011-2022 走看看