HDU

题意:给你一堆线段的长度,求任选三条能组成三角形的概率。

解法:先求出任选两条能组成的所有长度及其数量,这个过程可以用FFT实现。设a[i]代表长度为i的线段的数量,数组b为数组a的平方,然后从b中减去每条线段自己的贡献,即b[i*2]-=a[i],然后对所有的b[i]除以2,则b[i]就代表取两条线段长度和为i的方法数,剩下的用概率+前缀和搞一搞就行了。

 1 #include<bits/stdc++.h>
 2 using namespace std;
 3 typedef long long ll;
 4 typedef double db;
 5 const int N=4e5+10;
 6 const db pi=acos(-1);
 7 struct P {
 8     db x,y;
 9     P operator+(const P& b) {return {x+b.x,y+b.y};}
10     P operator-(const P& b) {return {x-b.x,y-b.y};}
11     P operator*(const P& b) {return {x*b.x-y*b.y,x*b.y+y*b.x};}
12     P operator/(db b) {return {x/b,y/b};}
13 } p[N];
14 void FFT(P* a,int n,int f) {
15     for(int i=1,j=n>>1,k; i<n-1; ++i,j^=k) {
16         if(i<j)swap(a[i],a[j]);
17         for(k=n>>1; j&k; j^=k,k>>=1);
18     }
19     for(int k=1; k<n; k<<=1) {
20         P wn= {cos(pi/k),f*sin(pi/k)};
21         for(int i=0; i<n; i+=k<<1) {
22             P w= {1,0};
23             for(int j=i; j<i+k; ++j,w=w*wn) {
24                 P x=a[j],y=w*a[j+k];
25                 a[j]=x+y,a[j+k]=x-y;
26             }
27         }
28     }
29     if(!~f)for(int i=0; i<n; ++i)a[i]=a[i]/n;
30 }
31 int n,m,mx;
32 ll a[N],b[N];
33 
34 int main() {
35     int T;
36     for(scanf("%d",&T); T--;) {
37         ll ans=0;
38         memset(a,0,sizeof a),mx=0;
39         scanf("%d",&n);
40         for(int i=0; i<n; ++i) {
41             int x;
42             scanf("%d",&x);
43             a[x]++;
44             mx=max(mx,x);
45         }
46         memset(p,0,sizeof p);
47         for(m=1; m<=2*mx; m<<=1);
48         for(int i=0; i<m; ++i)p[i]= {a[i],0};
49         FFT(p,m,1);
50         for(int i=0; i<m; ++i)p[i]=p[i]*p[i];
51         FFT(p,m,-1);
52         for(int i=0; i<m; ++i)b[i]=p[i].x+0.5;
53         for(int i=0; i<m; ++i)b[i*2]-=a[i];
54         for(int i=0; i<m; ++i)b[i]/=2;
55         for(int i=m-1; i>=0; --i)a[i]+=a[i+1];
56         for(int i=0; i<m; ++i)ans+=a[i]*b[i];
57         printf("%.7f
",1-ans*1.0/n/(n-1)/(n-2)*6);
58     }
59     return 0;
60 }
原文地址:https://www.cnblogs.com/asdfsag/p/10502745.html