原题链接
思路
我们观察数据范围,n为1e5,如果暴力匹配 n2 最坏 1e10 肯定会超时,下面两种解法都可以
1.哈希,借助数据结构的哈希,将每个ai放入unordered_map<int ,int> mp 中,值是出现的次数
2.有两种情况满足条件:a[i]在mp集合中,m-a[i]也在mp集合中,并且两者不相同 还有就是a[i]*2=m,并且mp[a[i]]>1
3.题中要求在满足条件的情况下,a[i]尽可能的小,所以先对a数组从小到大排序
1.双指针,要满足题中最小,先将数组排序
2.定义指针l,r 分别指向数组的开始与末尾,a[l]+a[r] 小于m,l++ ,大于m,r–, 直到找到答案,否则输出不可能
AC代码
哈希代码
#include<bits/stdc++.h>
using namespace std;
const int N=1e5+10;
int n,m;
int a[N];
unordered_map<int,int> mp;
int main(){
cin>>n>>m;
for(int i=1;i<=n;i++){
cin>>a[i];
mp[a[i]]++;
}
sort(a+1,a+1+n);
bool flag= false;
for(int i=1;i<=n;i++){
if((mp.count(a[i])&&mp.count(m-a[i])&&a[i]!=m-a[i])||(mp.count(a[i])&&a[i]*2==m&&mp[a[i]]>1)){
flag= true;
cout<<a[i]<<" "<<m-a[i]<<endl;
break;
}
}
if(!flag) cout<<"No Solution"<<endl;
return 0;
}
双指针代码
#include <iostream>
#include <map>
#include <algorithm>
using namespace std;
const int N = 100010;
int a[N];
int n,m;
int main()
{
cin >> n >> m;
for (int i = 0; i < n; i++) { cin >> a[i];}
sort(a,a+n);
int l = 0; int r = n - 1;
while (l < r) {
if (a[l] + a[r] > m) { r--; }
else if (a[l] + a[r] < m) { l++;}
else if (a[l] + a[r] == m) {break;}
}
if (l < r) {
cout << a[l] << " " << a[r] << endl;
}else{
cout << "No Solution" << endl;
}
return 0;
}