题意:给出一堆数,问从这些数中取3个能组成三角形的概率?
sol:其实就是问从这些数里取3个组成三角形有多少种取法
脑洞大开的解法:用FFT
设一开始的数是1 3 3 4
作一个向量x,其中x[i]=边长为i的边的个数
那么就有x=[0 1 0 2 1 0 0 0 0]
令y=x,对x和y作DFT,得到dx和dy。令dn=dx*dy,再对dn作IDFT得到n
那么就得到n=[0 0 1 0 4 2 4 4 1 0 ]
其中n[i]=在x和y中各选一条边,使得两条边之和为i有几种方案
这时得到的n并不好,包含了各种重复的方案。还得减一下
最后得到的n=[0 0 0 0 2 1 1 2 0]
然后对n做奇怪的操作。。。
先求前缀和,得到S
对于a[i]. 我们假设a[i]是形成的三角形中最长的。这样就是在其余中选择两个和>a[i],而且长度不能大于a[i]的。(注意这里所谓的大于小于,不是说长度的大于小于,其实是排好序以后的,位置关系,这样就可以不用管长度相等的情况,排在a[i]前的就是小于的,后面的就是大于的)。 根据前面求得的结果。 长度和大于a[i]的取两个的取法是sum[len]-sum[a[i]]. 但是这里面有不符合的。 一个是包含了取一大一小的 cnt -= (long long)(n-1-i)*i; 一个是包含了取一个本身i,然后取其它的 cnt -= (n-1); 还有就是取两个都大于的了 cnt -= (long long)(n-1-i)*(n-i-2)/2;