📌  相关文章
📜  找出总和为给定值的四个元素 |两点法

📅  最后修改于: 2021-09-05 08:43:07             🧑  作者: Mango

给定一个大小为N的整数数组 arr和一个目标数,任务是找到其中所有唯一的四元组,其总和等于目标数。

例子:

两点法:
这个问题遵循两个指针模式并且与三元组和为零有相似之处。

我们可以按照类似的方法遍历数组,一次取一个数字。在迭代过程中的每一步,我们将搜索类似于三元组和为零的四元组,其总和等于给定的目标。

C++
// C++ program to find four
// elements that sum to a given value
  
#include 
using namespace std;
  
class QuadrupleSumToTarget {
  
public:
    // Function to find quadruplets
    static vector >
    searchQuadruplets(
        vector& arr,
        int target)
    {
        sort(arr.begin(), arr.end());
        vector > quadruplets;
  
        for (int i = 0; i < arr.size() - 3; i++) {
            if (i > 0 && arr[i] == arr[i - 1]) {
  
                // Skip same element
                // to avoid duplicate
                continue;
            }
  
            for (int j = i + 1; j < arr.size() - 2; j++) {
                if (j > i + 1 && arr[j] == arr[j - 1]) {
  
                    // Skip same element
                    // to avoid duplicate quad
                    continue;
                }
                searchPairs(
                    arr, target,
                    i, j, quadruplets);
            }
        }
        return quadruplets;
    }
  
private:
    // Function to search Quadruplets
    static void
    searchPairs(
        const vector& arr,
        int targetSum, int first,
        int second,
        vector >& quadruplets)
    {
        int left = second + 1;
        int right = arr.size() - 1;
  
        while (left < right) {
            int sum
                = arr[first]
                  + arr[second]
                  + arr[left]
                  + arr[right];
  
            if (sum == targetSum) {
  
                // Found the quadruplet
                quadruplets
                    .push_back(
                        { arr[first], arr[second],
                          arr[left],
                          arr[right] });
                left++;
                right--;
  
                // Skip same element to avoid
                // duplicate quadruplets
                while (left < right
                       && arr[left]
                              == arr[left - 1]) {
                    left++;
                }
  
                // Skip same element to avoid
                // duplicate quadruplets
                while (left < right
                       && arr[right]
                              == arr[right + 1]) {
                    right--;
                }
            }
  
            // We need a pair
            // with a bigger sum
            else if (sum < targetSum) {
                left++;
            }
  
            // We need a pair
            // with a smaller sum
            else {
                right--;
            }
        }
    }
};
  
void printQuad(
    vector& vec, int target)
{
  
    // Function call
    auto result
        = QuadrupleSumToTarget::
            searchQuadruplets(
                vec, target);
  
    // Print Quadruples
    for (int j = 0; j < result.size(); j++) {
        vector vec = result[j];
        if (j == 0)
            cout << "[";
  
        for (int i = 0; i < vec.size(); i++) {
  
            if (i == 0)
                cout << "[";
            cout << vec[i];
            if (i != vec.size() - 1)
                cout << ", ";
            else
                cout << "]";
        }
  
        if (j != result.size() - 1)
            cout << ", ";
        else
            cout << "]";
    }
}
  
// Driver code
int main(int argc, char* argv[])
{
    vector vec
        = { 4, 1, 2,
            -1, 1, -3 };
    int target = 1;
  
    printQuad(vec, target);
  
    return 0;
}


输出:
[[-3, -1, 1, 4], [-3, 1, 1, 2]]

时间复杂度:对数组进行排序需要O(N*logN) 。总体而言searchQuadruplets()将采用O(N * logN + N^3) ,这与O(N^3)渐近等效。

辅助空间复杂度:上述算法的辅助空间复杂度为排序所需的O(N)。

类似文章:

  1. 找出总和为给定值的四个元素 |设置 1(n^3 解决方案)
  2. 找出总和为给定值的四个元素 |设置 2(O(n^2Logn) 解决方案)
  3. 找出总和为给定值的四个元素 |设置 3(哈希图)

如果您想与行业专家一起参加直播课程,请参阅Geeks Classes Live