赞
踩
- bool judge(int *arr,int n){
- for(int i = 0;i<n-2;++i){
- for(int j = i+1;j<n-1;++j){
- for(int k = j+1;k<n;++k)
- if(arr[i]+arr[j]+arr[k]==0)
- return true;
- }
- }
- return false;
- }
很显然这样的方法是不推荐的,复杂度太高。
改进1:首先对原数组进行排序,再用两层for循环固定前面两个数,然后第三个数用和减去前面2个数,最后采用二分查找的方法检查是否存在。该方法的复杂度为O(n^2*log(n))。
改进2:首先对原数组进行排序,除去一个固定的数字之后剩下两个数字,然后用两个指向数组的指针,一个从前往后扫描,一个从后往前扫描,记为first和last,如果 fist + last < sum 则将fist向前移动,如果fist + last > sum,则last向后移动。该方法的复杂度为O(n^2)。代码如下:
- #include <iostream>
- #include <algorithm>
- using namespace std;
-
- void printPairSums(int data[], int size, int sum)
- {
- int first = 0;
- int last = size -1;
- int s = 0;
- while (first < last)
- {
- s = data[first] + data[last];
- if (s == sum)
- {
- cout << data[first] << " + " << data[last] << " = " << sum << endl;
- first++;
- last--;
- }
- else if (s < sum)
- first++;
- else
- last--;
- }
- }
-
- int main(int argc, char* argv[])
- {
- int data[] = {1, 5, 9, -1, 4, 6, -2, 3, -8};
- int size = sizeof(data) / sizeof(data[0]);
- int i;
- sort(data, data + size);
- printPairSums(data, size, 8);
-
- system("pause");
- return 0;
- }
改进3:采用回溯法。代码如下:
- #include <iostream>
- #include <algorithm>
- using namespace std;
-
- const int S = 22;
-
- int sumCheck(int A[], int start, int end, int arr[], int cnt){
- if (cnt == 2){
- int sum = arr[0] + arr[1] + arr[2];
- if (sum == S)
- cout << arr[0] << "\t" << arr[1] << "\t" << arr[2] << endl;
- return 0;
- }
- if (start > end || cnt > 2)
- return -1;
-
- int i = start;
- arr[++cnt] = A[i];
- sumCheck(A, start + 1, end, arr, cnt);
- arr[cnt] = 0;
- cnt--;
- sumCheck(A, start + 1, end, arr, cnt);
- }
- int main(int argc, char* argv[])
- {
- int A[] = {1, 4, 45, 6, 10, 8};
- int arr_size = sizeof(A) / sizeof(A[0]);
- int cnt = -1;
- int arr[3] = {0, 0, 0};
-
- sumCheck(A,0, arr_size-1, arr, cnt);
-
- system("pause");
- return 0;
- }
问题的推广可参考博客求数组中多个数相加等于某一值以及面试题:检查一个数组里是否存在m个数的和等于某个值。
Copyright © 2003-2013 www.wpsshop.cn 版权所有,并保留所有权利。