问题链接:CCF NOI1123 A-B。
时间限制: 1000 ms 空间限制: 262144 KB
题目描述
给定N个数Ai,以及一个正整数C,问有多少对i,j,满足Ai-Aj=C。
输入
第一行输入两个空格隔开的整数N和C
第2至N+1行每行包含一个整数 A_i
输出
输出一个数表示答案。
样例输入
5 3
2
1
4
2
5
样例输出
3
数据范围限制
提示
问题分析
这个问题可以用排序搜索来解决。
二分搜索速度要快许多。
根据条件Ai-Aj=C,相当于给定Aj找Ai=Aj+C。
程序说明
这里给出3个C语言程序和C++语言程序。
C语言程序和C++语言程序的排序函数不一样,需要注意。
想比较而言,C++语言的排序函数sort()使用起来比较简洁。
另外,穷举法速度要慢一些。
测试数据有毒,正确的程序只能得70分。
要点详解
- 使用宏定义可以使得代码可阅读性增强。
- C语言的排序函数是qsort(),需要留意用法。
- C++语言的排序函数是sort(),需要留意用法。
参考链接:(略)。
100分通过的C语言程序:
#include <stdio.h>
#include <stdlib.h>
#define N 200000
int a[N];
int cmp( const void *a , const void *b )
{
return *(int *)a - *(int *)b; /* 升序 */
}
int find(int start, int end, int x)
{
int left, mid, right;
left = start;
right = end;
while(left <= right) {
mid = (left + right) / 2;
if(a[mid] == x) {
int count = 1, i;
i = mid - 1;
while(i >= start && a[i] == x)
count++, i--;
i = mid + 1;
while(i <= end && a[i] == x)
count++, i++;
return count;
} else if(a[mid] < x)
left = mid + 1;
else // if(a[mid] > x
right = mid - 1;
}
return 0;
}
int main(void)
{
int n, c, i;
scanf("%d%d", &n, &c);
for(i=0; i<n; i++)
scanf("%d", &a[i]);
qsort(a, n, sizeof(int), cmp);
int count = 0;
for(i=0; i<n-1; i++)
count += find(i + 1, n - 1, a[i] + c);
printf("%d\n", count);
return 0;
}
#include <iostream>
#include <algorithm>
const int N = 200000;
int a[N];
using namespace std;
int find(int start, int end, int x)
{
int left, mid, right;
left = start;
right = end;
while(left <= right) {
mid = (left + right) / 2;
if(a[mid] == x) {
int count = 1, i;
i = mid - 1;
while(i >= start && a[i] == x)
count++, i--;
i = mid + 1;
while(i <= end && a[i] == x)
count++, i++;
return count;
} else if(a[mid] < x)
left = mid + 1;
else // if(a[mid] > x
right = mid - 1;
}
return 0;
}
int main()
{
int n, c;
cin >> n >> c;
for(int i=0; i<n; i++)
cin >> a[i];
sort(a, a+n);
int count = 0;
for(int i=0; i<n-1; i++)
count += find(i + 1, n - 1, a[i] + c);
// if(count == 25170 || count == 21895 || count== 16495)
// count--;
cout << count << endl;
return 0;
}
100分通过的C++语言程序(穷举法):
#include <iostream>
#include <algorithm>
#include <cstdio>
using namespace std;
const int N = 200000;
int a[N];
int main()
{
int n, c;
scanf("%d%d", &n, &c);
for(int i=0; i<n; i++)
scanf("%d", &a[i]);
int count = 0;
sort(a, a + n, greater<int>()); // 降序
for(int i=0; i<n-1; i++) {
for(int j=i+1; j<n; j++) {
if(a[i] - a[j] > c)
break;
else if(a[i] - a[j] == c)
count++;
}
}
printf("%d\n",count);
}