题目描述
阿美的老师要对天才少女阿美进行极限测试,老师随便给出一个整数m和若干个递增排序的整数序列(里面有好多好多数啊!),老师要求阿美快速观察并回答出在这个递增的整数序列中是否存在两个不相同的数a和b,满足a+b=m,如果存在则给出这两个数,否则说No。阿美思来想去无法解决,请你帮帮她吧,她可是个校花啊!
Input
第一行是整数n(0 < n <= 100,000)。
第二行是n个递增排序的整数。整数的范围是在0到10^8之间。
第三行是一个整数k(0 < k <= 100),代表有k次查询。
接下来有k行,每行一个整数m(0 <= m <= 10^9)。
Output
k行,每行对应一个整数m的划分结果。对于每一个m,在给出的n个递增排序的整数中若存在和为m的两个不相同的数,输出这两个整数。若存在多个两个整数之和等于m的情况,则选择较小的数更小的那一对。若在n个数中找不到和为m的两个不相同的整数,则输出No。
Sample Input
5
2 3 4 5 5
4
7
4
6
10
Sample Output
2 5
No
2 4
No
Solve
普通方法会超时。
用二分法,注意循环数组时,要从当前下标开始查询
(我是从0开始找的,十多遍都不对)
代码
#include<stdio.h>
int search(int a[],int x,int low,int high)
{
if(low>high)
{
return -1;
}
else
{
int mid=(low+high)/2;
if(x==a[mid])
{
return mid;
}
if(x<a[mid])
{
return search(a,x,low,mid-1);
}
else
{
return search(a,x,mid+1,high);
}
}
}
int main()
{
int n,k,a[100007],m;
scanf("%d",&n);
for(int i=0;i<n;i++)scanf("%d",&a[i]);
scanf("%d",&k);
for(int l=0;l<k;l++)
{
scanf("%d",&m);
int x,y,z,j,flag=0;
for(j=0;j<n;j++)
{
y=n-1;
x=m-a[j];
if(x==a[j])continue;
flag=search(a,x,j,y);
if(flag!=-1)
{
break;
}
}
if(flag!=-1)
{
printf("%d %d\n",a[j],x);
}
else
{
printf("No\n");
}
}
return 0;
}