码蹄杯 距离平方和 题型:数论 难度:黄金

73 阅读1分钟

码题集OJ-距离平方和 (matiji.net)

推算

求两个点之间的距离公式为:

dist=(x1x2)2(y1y2)2dist=\sqrt{(x1-x2)^2-(y1-y2)^2}

因为题目求的是距离的平方和,因此,我们可以不用要根号了,直接写为如下:

dist2=(x1x2)2(y1y2)2dist^2=(x1-x2)^2-(y1-y2)^2

然后我们就只看 (x1x2)2(x1-x2)^2这半部分:

这半部分可以展开为: x1+x22x1x2x1+x2-2x1*x2

这个公式又可以拆为:x1+x2x1+x2 2x1x2-2x1*x2 两部分。

先看x1+x2x1+x2这部分。因为有n个点,每个点都要求与其他点的距离。 因此这部分要(n1)*(n-1)

再看2x1x2 2x1*x2这部分,同样因为有n个点,因此可以表示为:

2x1x2+2x2xi+2x3xi+2xnxi2x1*x2 + 2x2 * xi +2x3*xi + ……2xn* xi

然后我们把2和xi提取出来,变为如下: 2xi(x1+x2+x3+x4+x5++xn)2xi(x1+x2+x3+x4+x5+……+xn)

我们发现 x1+x2+x3+x4++xnx1+x2+x3+x4+……+xn可以用前缀和去求。

code

#include<bits/stdc++.h>
#define int long long
using namespace std;
int ans;
int sx,sy,n;
signed main()
{
	cin>>n;
	for(int i=0;i<n;i++)
	{
		int x,y;cin>>x>>y;
		
		ans+=(n-1)*(x*x+y*y)-((x*sx+y*sy)*2);
		sx+=x,sy+=y;
	}
	cout<<ans;
	
	return 0;
}

image.png