HDU 4609 FFT模板
http://acm.hdu.edu.cn/showproblem.php?pid=4609
题意:给你n个数,问任意取三边能够,构成三角形的概率为多少。
思路:使用FFT对所有长度的个数进行卷积(\(C = \{x + y| x \in A, y \in B \} \)),得到所有两边和情况数,再考虑去掉重复的情况。找边并计数的时候再去掉不可能的情况。具体操作看bin神的博客
另FFT还可以用来进行多项式和高精度乘法,又难懂又难用的东西=x=
/** @Date : 2016-12-04-16.31
* @Author : Lweleth (SoungEarlf@gmail.com)
* @Link : https://github.com/
* @Version :
*/ #include<bits/stdc++.h>
#define LL long long
#define PII pair
#define MP(x, y) make_pair((x),(y))
#define fi first
#define se second
#define PB(x) push_back((x))
#define MMG(x) memset((x), -1,sizeof(x))
#define MMF(x) memset((x),0,sizeof(x))
#define MMI(x) memset((x), INF, sizeof(x))
using namespace std; const int INF = 0x3f3f3f3f;
const int N = 1e5+20;
const double eps = 1e-8;
const double PI = acos(-1.0); struct Complex
{
double a, i;//实部,虚部
Complex(double aa = 0, double ii = 0)
{
a = aa, i = ii;
}
Complex operator +(const Complex &y)
{
return Complex(a + y.a, i + y.i);
}
Complex operator -(const Complex &y)
{
return Complex(a - y.a, i - y.i);
}
Complex operator *(const Complex &y)
{
return Complex(a * y.a - i * y.i, a * y.i + i * y.a);
}
}; void change(Complex y[], int len)//len 必须为2的幂;位置i和二进制反转的位置互换
{
int i, j, k;
for(i = 1, j = len / 2; i < len - 1; i++)
{
if(i < j)
swap(y[i], y[j]);
//交换互为小标反转的元素,i<j交换一次
//i正常++ j左反转类型的+1 始终保持二者反转
k = len / 2;
while(j >= k)
{
j -= k;
k /= 2;
}
if(j < k)
j += k;
}
} void fft(Complex y[], int len, int on)//on==1时DFT -1时IDFT len必须为2的幂
{
change(y, len);
for(int h = 2; h <= len; h <<= 1)
{
Complex wn(cos(-on * 2 * PI / h), sin(-on * 2 * PI / h));
for(int j = 0; j < len; j+=h)
{
Complex w(1, 0);
for(int k = j; k < j + h / 2; k++)
{
Complex u = y[k];
Complex t = w * y[k + h / 2];
y[k] = u + t;
y[k + h / 2] = u - t;
w = w * wn;
}
}
}
if(on == -1)
for(int i = 0; i < len; i++)
y[i].a /= len;
} Complex x1[4 * N];
int a[N];
LL num[4 * N];
LL sum[4 * N]; int main()
{
int T;
cin >> T;
while(T--)
{
int n;
scanf("%d", &n);
MMF(num);
for(int i = 0; i < n; i++)
{
scanf("%d", a + i);
num[a[i]]++; }
sort(a, a + n);
////
int len1 = a[n - 1] + 1;
int len = 1;
while(len < 2 * len1)
len <<= 1;
for(int i = 0; i < len1; i++)
x1[i] = Complex(num[i], 0);
for(int i = len1; i < len; i++)
x1[i] = Complex(0 , 0);
//
fft(x1, len, 1);
for(int i = 0; i < len; i++)
x1[i] = x1[i] * x1[i];
fft(x1, len, -1);
//
for(int i = 0; i < len; i++)
num[i] = (LL)(x1[i].a + 0.5);
len = 2 * a[n - 1]; /////
for(int i = 0; i < n; i++)//卷积中同样的数字选取两次
num[a[i] + a[i]]--;
for(int i = 1; i <= len; i++)//卷积中数字选取无顺序关系
num[i] /= 2;
sum[0] = 0;
for(int i = 1; i <= len; i++)//数字出现次数前缀和
{
sum[i] = sum[i - 1] + num[i];
}
LL cnt = 0;
for(int i = 0; i < n; i++)
{
cnt += sum[len] - sum[a[i]];
///
cnt -= (LL)(n - i - 1) * i;
cnt -= (LL)(n - 1) * 1;
cnt -= (LL)(n - i - 1) * (n - i - 2) / 2;
}
printf("%.7lf\n", (double)cnt * 6.0 / n / (n - 1.0) / (n - 2.0));
}
return 0;
}
HDU 4609 FFT模板的更多相关文章
- hdu 4609 FFT
题意:给出一堆数,问从这些数中取3个能组成三角形的概率? sol:其实就是问从这些数里取3个组成三角形有多少种取法 脑洞大开的解法:用FFT 设一开始的数是1 3 3 4 作一个向量x,其中x[i]= ...
- HDU 1402 fft 模板题
题目就是求一个大数的乘法 这里数字的位数有50000的长度,按平时的乘法方式计算,每一位相乘是要n^2的复杂度的,这肯定不行 我们可以将每一位分解后作为系数,如153 = 1*x^2 + 5*x^1 ...
- HDU 4609 FFT+组合数学
3-idiots Time Limit: 10000/5000 MS (Java/Others) Memory Limit: 32768/32768 K (Java/Others)Total S ...
- HDU 4609 FFT+各种分类讨论
思路: http://www.cnblogs.com/kuangbin/archive/2013/07/24/3210565.html 其实我是懒得写了.... 一定要define int long ...
- hdu 4609 3-idiots [fft 生成函数 计数]
hdu 4609 3-idiots 题意: 给出\(A_i\),问随机选择一个三元子集,选择的数字构成三角形的三边长的概率. 一开始一直想直接做.... 先生成函数求选两个的方案(注意要减去两次选择同 ...
- fft模板 HDU 1402
// fft模板 HDU 1402 #include <iostream> #include <cstdio> #include <cstdlib> #includ ...
- HDU 4609 3-idiots FFT+容斥
一点吐槽:我看网上很多分析,都是在分析这个题的时候,讲了半天的FFT,其实我感觉更多的把FFT当工具用就好了 分析:这个题如果数据小,统计两个相加为 x 的个数这一步骤(这个步骤其实就是求卷积啊),完 ...
- HDU 1402 A * B Problem Plus (FFT模板题)
FFT模板题,求A*B. 用次FFT模板需要注意的是,N应为2的幂次,不然二进制平摊反转置换会出现死循环. 取出结果值时注意精度,要加上eps才能A. #include <cstdio> ...
- HDU 4609 3-idiots ——(FFT)
这是我接触的第一个关于FFT的题目,留个模板. 这题的题解见:http://www.cnblogs.com/kuangbin/archive/2013/07/24/3210565.html. FFT的 ...
随机推荐
- Thunder团队第一周 - Scrum会议7
Scrum会议7 小组名称:Thunder 项目名称:爱阅app Scrum Master:宋雨 工作照片: 参会成员: 王航:http://www.cnblogs.com/wangh013/ 李传康 ...
- PART1 一些想法
其实我一直是一个后知后觉的人,这点也是我过了好久才发现的问题,之所以晚发现自己这个毛病,是因为后知后觉==,这有点像是个悖论或者是笑话,但的确是真实存在于我的身上.其实当初为啥来这个学校选计算机的专业 ...
- LintCode-165.合并两个排序链表
合并两个排序链表 将两个排序链表合并为一个新的排序链表 样例 给出 1->3->8->11->15->null,2->null, 返回 1->2->3- ...
- Unity3d学习日记(五)
之前用3dsmax将模型转成FBX怎么也没有办法自动导入材质到Unity3d中(试过勾选了导出嵌入媒体,没用).索性试了试c4d,发现是可行的,看来像我这种菜鸡还是更加适合用c4d. 拿zoe ...
- lol人物模型提取(二)
两个dds文件怎么导入到一个模型上呢?这模型又不能拆开. 一开始我想的是用两个材质球来完成,一个材质球对应一个dds文件,然而行不通. 一个材质球对应两个dds文件还不太会弄,于是我想着干 ...
- Qt-excel文件操作方法
版权声明:若无来源注明,Techie亮博客文章均为原创. 转载请以链接形式标明本文标题和地址: 本文标题:Qt-excel文件操作方法 本文地址:http://techieliang.com/ ...
- node.js cmd 输入npm-v无反应
今天安装node,先是提示node版本太低.去官网更新了一下,然后 npm install -g vue-cli 结果出了个"npm ERR! errno -4048" 百度出 这 ...
- jconsole工具监控数据分析
当Jconsole连接成功后,它从JMX获取信息,我们便可以在里面监控具体的内容.Jconsole能捕获到以下信息: 概述 - JVM概述和一些监控变量的信息 内存 - 内存的使用信息 线程 - 线程 ...
- PHPCMSV9 黄页新闻、产品、商机均无法浏览具体信息,显示您没有访问该信息的权限!
原帖地址:http://bbs.phpcms.cn/forum.php?mod=viewthread&tid=294956&highlight=%C3%BB%D3%D0%B7%C3%C ...
- 含html转义字符编码(四)转换--python
在抓取下来的网页源码显示的是如下的内容,而不是可读性的汉字 (当然,如果是在Web页面上展示,则实体会自动被浏览器转为原字符,正常显示) 经查资料后得知, 在网页中以四开头的是HTML实体,具体什么是 ...