很经典的一道算法题,我没想出来。。。
看了答案做出来的,二分法真强大,还有就是一定注意下边界条件,如果cal返回k则不一定是前k小,有可能没有这个数字,所以还要进一布减小。
#include <iostream>
#include <queue>#include <iomanip>
#include <vector>
#include <queue>
#include <map>
#include <stack>
#include <cstdio>
#include <algorithm>
#include <cmath>
#include <set>
#include <sstream>
#include <cstring>
using namespace std;
long long nums1[100001];
long long nums2[100001];
int m,n;
long long cal(long long val)
{
int j=n;
long long add=0;
for(int i=1;i<=m;i++)
{
if(j==0)
break;
while(j>=1&&(nums1[i]+nums2[j])>val)
j--;
add+=j;
}
return add;
}
int main()
{
long long k;
while(cin>>m>>n>>k)
{
for(int i=1;i<=m;i++)
cin>>nums1[i];
for(int i=1;i<=n;i++)
cin>>nums2[i];
long long mmin=nums1[1]+nums2[1];
long long mmax=nums1[m]+nums2[n];
int mid;
while(mmin<=mmax)
{
mid=(mmin+mmax)/2;
if(cal(mid)<k)
{
mmin=mid+1;
}
else if(cal(mid)>=k)
{
mmax=mid-1;
}
}
cout<<mmin<<endl;
}
return 0;
}