Points on Line(CF-252C)
Problem Description
Little Petya likes points a lot. Recently his mom has presented him n points lying on the line OX. Now Petya is wondering in how many ways he can choose three distinct points so that the distance between the two farthest of them doesn't exceed d.
Note that the order of the points inside the group of three chosen points doesn't matter.
Input
The first line contains two integers: n and d (1 ≤ n ≤ 105; 1 ≤ d ≤ 109). The next line contains n integers x1, x2, ..., xn, their absolute value doesn't exceed 109 — the x-coordinates of the points that Petya has got.
It is guaranteed that the coordinates of the points in the input strictly increase.
Output
Print a single integer — the number of groups of three points, where the distance between two farthest points doesn't exceed d.
Please do not use the %lld specifier to read or write 64-bit integers in С++. It is preferred to use the cin, cout streams or the %I64d specifier.
Examples
Input
4 3
1 2 3 4Output
4
Input
4 2
-3 -2 -1 0Output
2
Input
5 19
1 10 20 30 50Output
1
Note
In the first sample any group of three points meets our conditions.
In the seconds sample only 2 groups of three points meet our conditions: {-3, -2, -1} and {-2, -1, 0}.
In the third sample only one group does: {1, 10, 20}.
题意:给出一个长度为 n 的递增集合,现在要在集合中取出 3 个数,使得最大数与最小数的差值小于 d,问有多少种取法
思路:
假设一个长度从 1~m 的区间,区间内的任意两个数做差均小于 d,那么有 C(m,2) 种选法
现在已知集合递增,那么从每个数的位置 i 开始,二分查找后面最大的两者距离不超过 d 的数的位置 pos,然后在这个区间内有 C(pos-i,2) 种选法,求和即可
Source Program
#include<iostream>
#include<cstdio>
#include<cstdlib>
#include<string>
#include<cstring>
#include<cmath>
#include<ctime>
#include<algorithm>
#include<utility>
#include<stack>
#include<queue>
#include<vector>
#include<set>
#include<map>
#include<bitset>
#define EPS 1e-9
#define PI acos(-1.0)
#define INF 0x3f3f3f3f
#define LL long long
#define Pair pair<int,int>
const int MOD = 1E9+7;
const int N = 100000+5;
const int dx[] = {-1,1,0,0,-1,-1,1,1};
const int dy[] = {0,0,-1,1,-1,1,-1,1};
using namespace std;
int a[N];
int main() {
int n,k;
scanf("%d%d",&n,&k);
for(int i=1; i<=n; i++)
scanf("%d",&a[i]);
LL res=0;
for(int i=1; i<=n-2; i++) {
LL pos=upper_bound(a+i,a+1+n,a[i]+k)-a-1;
res+=(pos-i)*(pos-i-1)/2;
}
printf("%lld\n",res);
return 0;
}
【推荐】博客园的心动:当一群程序员决定开源共建一个真诚相亲平台
【推荐】国内首个AI IDE,深度理解中文开发场景,立即下载体验Trae
【推荐】Flutter适配HarmonyOS 5知识地图,实战解析+高频避坑指南
【推荐】凌霞软件回馈社区,携手博客园推出1Panel与Halo联合终身会员
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步