题目如下:
这道题我们最先想到的做法,应该就是2重循环枚举数对,然后把数对放在set里去重,最后输出set的大小,即输出set.size( )。
代码如下:
代码如下:
1 #include<iostream> 2 #include<set> 3 using namespace std; 4 5 int n, k, a[100000]; 6 set<pair<int, int>> mypairs; 7 8 int main() 9 { 10 cin >> n >> k; 11 for(int i = 0; i < n; i ++) 12 cin >> a[i]; 13 for(int i = 0; i < n; i ++) 14 { 15 for(int j = 0; j < n; j ++) 16 { 17 if(a[i] + k == a[j]) 18 mypairs.insert(make_pair(a[i], a[j])); 19 } 20 } 21 cout << mypairs.size() << endl; 22 return 0; 23 }
通过使用哈希表进行枚举优化
优化后的思路:
如果我们只枚举a[i],比如a[i]=3,那么如果存在数对的话,这个数对肯定是(a[i], a[i]+k)。比如样例里,假设我枚举数对里较小的值是3,那根据差是2,较大的肯定是5。所以,问题就变成,查找a[i]+k在不在输入的数组里。
该代码(支持C++11标准):
针对这样的问题,哈希表是一个非常好用的工具。而且更方便的是,C++的STL已经帮我们把这些工具都实现好了,提供了非常方便的接口,我们直接用行了。下面介绍一下unordered_set,unordered_set可以把它想象成一个集合,它提供了几个函数让我们可以增删查:
unordered_set::insert、
unordered_set::find、
unordered_set::erase.....
1 #include<iostream> 2 #include<unordered_set> 3 using namespace std; 4 5 int n, k, x, ans = 0; 6 unordered_set<int> myset; 7 8 int main() 9 { 10 cin >> n >> k; 11 12 for(int i = 0; i < n; i ++) 13 { 14 cin >> x; 15 myset.insert(x); 16 } 17 for(int x : myset) 18 { 19 if(myset.find(x+k) != myset.end()) 20 ans ++; 21 } 22 cout << ans << endl; 23 return 0; 24 }
或者:(编译器不支持C++11标准的代码)
1 #include<iostream> 2 #include<set> 3 using namespace std; 4 5 int n, k, x, ans = 0; 6 set<int> myset; 7 8 int main() 9 { 10 cin >> n >> k; 11 12 for(int i = 0; i < n; i ++) 13 { 14 cin >> x; 15 myset.insert(x); 16 } 17 for(set<int> ::iterator i = myset.begin(); i != myset.end(); i ++) 18 { 19 if(myset.find((*i)+k) != myset.end()) 20 ans ++; 21 } 22 cout << ans << endl; 23 return 0; 24 }
运行结果图如下: