BZOJ4827 [Hnoi2017]礼物 多项式 FFT
原文链接http://www.cnblogs.com/zhouzhendong/p/8823962.html
题目传送门 - BZOJ4827
题意
有两个长为$n$的序列$x$和$y$,序列$x,y$的第$i$项分别是$x_i,y_i$。
选择一个序列$A$,现在你可以对它进行如下两种操作:
$1.$ 得到一个和$A$循环同构的序列$A'$。
$2.$ 给所有的$A'_i$都加上$c(c\in N^+)$,得到序列$A''$。
你进行上面两个操作之后,得到的序列分别为$x'',y''$(注意$x,y$两个序列中至少有一个序列没有发生任何变化)
序列$x''$和$y''$的差异值为
$$\sum_{i=1}^{n}(x''_i-y''_i)^2$$
问差异值最小为多少。
题解
我们可以选择任何一个序列进行那两个操作就是相当于对$x$进行操作$1$和下面这个操作:
$2'.$ 给所有的$x'_i$都加上$c(c\in Z)$,得到序列$x''$。
于是:
$$\sum_{i=1}^{n}(x''_i-y_i)^2$$
$$=\sum_{i=1}^{n}(x'_i-y_i+c)^2$$
(假装后面的没有'的就当有吧,公式不知道为啥烂掉了)
$$=\sum_{i=1}^{n}x_i^2+y_i^2+c^2-2x_iy_i+2(x_i-y_i)c$$
$$=\sum_{i=1}^{n}x_i^2+y_i^2+c^2+(\sum_{i=1}^{n}(x_i-y_i))c-2x_iy_i$$
发现这是个关于$c$的二次函数再加上一坨$-2x'_iy_i$。
对于$c$只需要运用一下初中的数学知识即可。
具体地:
设$t=\sum_{i=1}^{n}x_i-y_i$.
则与$c$有关的式子是$nc^2+2tc$。
这个时候其实$-100$到$100$暴搜应该也可以的。
然后我们运用初中的数学配个方就可以快速算出$c$的取值,但是注意$c$为整数,所以我们就去周围几个数判几下就可以了。
对于后面的那个,只需要倍长$y$,翻转$x$,然后套路$FFT$即可。
具体地:
为了方便,下面把$x_i$和$y_i$下标看做从$0$开始。
首先化环为链,我们把$y$倍长。
然后构造多项式:
$$h_i=\sum_{j=0}^{n-1}x_jy_{i+j-1}$$
看起来可以用$FFT$来优化。
我们只需要翻转$x$数组,得到:
$$h_i=\sum_{j=0}^{n-1}x_{n-j-1}y_{i+j-1}$$
让$h_i$整体右移$n-1$位,再重新整理上式得:
$$h_i=\sum_{j=0}^{i}x_jy_{i-j}$$
显然这个可以$FFT$。
其中只有$h_{n-1}\dots h_{2n-2}$是有用的。
求出来之后,只要求下有效$h_i$的最大值$max$即可。然后让答案减掉$-2max$
代码
#include <bits/stdc++.h>
using namespace std;
typedef long long LL;
const int N=1<<18;
double PI=acos(-1.0);
int n,m,c,x[N],y[N],t=0;
int s,L,R[N];
LL ans=0,xymax=0;
struct C{
double r,i;
C(){}
C(double a,double b){r=a,i=b;}
C operator + (C x){return C(r+x.r,i+x.i);}
C operator - (C x){return C(r-x.r,i-x.i);}
C operator * (C x){return C(r*x.r-i*x.i,r*x.i+i*x.r);}
}w[N],A[N],B[N];
LL calc(LL c){
return c*c*n+c*t*2;
}
LL getc_val(int t,int n){
LL c1=-t/n,c2=c1+1,c3=c1-1;
return min(min(calc(c1),calc(c2)),calc(c3));
}
void FFT(C a[],int n){
for (int i=0;i<n;i++)
if (i<R[i])
swap(a[i],a[R[i]]);
for (int t=n>>1,d=1;d<n;d<<=1,t>>=1)
for (int i=0;i<n;i+=(d<<1))
for (int j=0;j<d;j++){
C tmp=w[t*j]*a[i+j+d];
a[i+j+d]=a[i+j]-tmp;
a[i+j]=a[i+j]+tmp;
}
}
int main(){
scanf("%d%d",&n,&m);
for (int i=0;i<n;i++)
scanf("%d",&x[i]);
for (int i=0;i<n;i++)
scanf("%d",&y[i]),t+=x[i]-y[i],ans+=x[i]*x[i]+y[i]*y[i];
ans+=getc_val(t,n);
for (s=1,L=0;s<n*3;s<<=1,L++);
for (int i=0;i<s;i++){
R[i]=(R[i>>1]>>1)|((i&1)<<(L-1));
w[i]=C(cos(2*i*PI/s),sin(2*i*PI/s));
A[i]=B[i]=C(0,0);
}
for (int i=0;i<n;i++)
A[i]=C(x[n-i-1],0),B[i]=B[i+n]=C(y[i],0);
FFT(A,s),FFT(B,s);
for (int i=0;i<s;i++)
A[i]=A[i]*B[i],w[i].i*=-1.0;
FFT(A,s);
for (int i=n-1;i<2*n;i++)
xymax=max(xymax,(LL)(A[i].r/s+0.5));
ans-=xymax*2;
printf("%lld",ans);
return 0;
}
BZOJ4827 [Hnoi2017]礼物 多项式 FFT的更多相关文章
- [BZOJ4827][Hnoi2017]礼物(FFT)
4827: [Hnoi2017]礼物 Time Limit: 20 Sec Memory Limit: 512 MBSubmit: 1315 Solved: 915[Submit][Status] ...
- [bzoj4827][Hnoi2017]礼物_FFT
礼物 bzoj-4827 Hnoi-2017 题目大意:给定两个长度为$n$的手环,第一个手环上的$n$个权值为$x_i$,第二个为$y_i$.现在我可以同时将所有的$x_i$同时加上自然数$c$.我 ...
- [HNOI2017] 礼物 - 多项式乘法FFT
题意:给定两个 \(n\) 元环,环上每个点有权值,分别为 \(x_i, y_i\).定义两个环的差值为 \[\sum_{i=0}^{n-1}{(x_i-y_i)^2}\] 可以旋转其中的一个环,或者 ...
- BZOJ4827: [Hnoi2017]礼物(FFT 二次函数)
题意 题目链接 Sol 越来越菜了..裸的FFT写了1h.. 思路比较简单,直接把 \(\sum (x_i - y_i + c)^2\) 拆开 发现能提出一坨东西,然后与c有关的部分是关于C的二次函数 ...
- BZOJ4827:[HNOI2017]礼物(FFT)
Description 我的室友最近喜欢上了一个可爱的小女生.马上就要到她的生日了,他决定买一对情侣手环,一个留给自己,一 个送给她.每个手环上各有 n 个装饰物,并且每个装饰物都有一定的亮度.但是在 ...
- 洛谷P3723 [AH2017/HNOI2017]礼物(FFT)
传送门 首先,两个数同时增加自然数值相当于只有其中一个数增加(此增加量可以小于0) 我们令$x$为当前的增加量,${a},{b}$分别为旋转后的两个数列,那么$$ans=\sum_{i=1}^n(a_ ...
- bzoj 4827: [HNOI2017]礼物 (FFT)
一道FFT 然而据说暴力可以水70分 然而我省选的时候看到了直接吓傻了 连暴力都没打 太弱了啊QAQ emmmm 详细的拆开就看其他题解吧233 最后那一步卷积其实我一直没明白 后来画画图终于懂了 ...
- bzoj4827 [Hnoi2017]礼物
Description 我的室友最近喜欢上了一个可爱的小女生.马上就要到她的生日了,他决定买一对情侣手 环,一个留给自己,一个送给她.每个手环上各有 n 个装饰物,并且每个装饰物都有一定的亮度.但是在 ...
- bzoj千题计划303:bzoj4827: [Hnoi2017]礼物
https://www.lydsy.com/JudgeOnline/problem.php?id=4827 式子化简一下,发现最后只跟 Σ xi*yi 有关 第二个序列反转,就可以用FFT优化 注意: ...
随机推荐
- jzoj6099. 【GDOI2019模拟2019.4.1】Dist
题目链接:https://jzoj.net/senior/#main/show/6099 考虑直接统计某个点到其它所有点的距离和 我们先把整个团当成一个点建图,处理出任意两个团之间的距离\(dis(i ...
- Django 信号
信号 Django 提供一个“信号分发器”,允许解耦的应用在框架的其它地方发生操作时会被通知到. 简单来说,信号允许特定的sender通知一组receiver某些操作已经发生. 这在多处代码和同一事件 ...
- Yii2的Gridview应用技巧补充
Yii2框架下的Gridview通常用来展示一张DB表中的数据,十分方便.这里只说一下经常要用到的一些小技巧,其实大多数官方文档都是有的,只是有可能需要在多个文档里. 自动创建的gridview示例. ...
- tensorflow 语音识别报错
cuDnn由7.1版本改为7.4.2.24版本,成功
- 常用js方法整理(个人)
开头总要有点废话 今天想了下,还是分享下自己平时积累的一些实用性较高的js方法,供大家指点和评价.本想分篇介绍,发现有点画蛇添足.整理了下也没多少拿得出手的方法,自然有一些是网上看到的个人觉得很有实用 ...
- mtd-utils 安装
title: mkdosfs 安装 tags: linux date: 2018/12/26/ 17:08:54 --- mtd-utils安装 for 主机 在制作根文件系统中需要使用它制作jffs ...
- JAVA IO练习
停车场有进场和出场的功能1. 进场时:采用键盘录入的方式,录入汽车的品牌.颜色.车牌号. 把品牌.颜色.车牌号,以及进场时间写入car.txt文件中. 2. 出场时:键盘录入车牌号,去文件中查找该车 ...
- 第八节:常见安全隐患和传统的基于Session和Token的安全校验
一. 常见的安全隐患 1. SQL注入 常见的案例: String query = "SELECT * FROM T_User WHERE userID='" + Request ...
- [译]Ocelot - Routing
原文 Ocelot主要的功能就是将http请求转发到对应的下游服务上去. Ocelot将一个请求路由到另外一个路由的动作叫做ReRoute.为了能让Ocelot能正常工作,需要在配置中设置ReRout ...
- 入门嵌入式选择2440?树莓派?STM32?4412开发板?
如果了解一下当前IT和物联网发展的形势,就会发现Android工程师越来越受欢迎,相比之下单纯的Linux工程师却逊色不少,当然,Android系统的内核也是Linux的,Linux和Android作 ...