Binary Search vs. Two Pointers
In the first approach, we sort potions, and use binary search to find the position of the weakest potion that produces a success. All potions to the right would
In the first approach, we sort `potions`, and use binary search to find the position of the weakest potion that produces a success. All potions to the right would work also.\n\nIn the second approach, we sort both `potions` and `spells` (we actually sort indexes `idx` to preserve the order of spells). Then, we use two pointers to track the weakest  `potions[j]` that works for `spells[i]`. Since we process spells from weakest to the strongest, pointer `j` is moved in one direction - from strongest to weakest.\n\n#### Binary Search\n**C++**\n```cpp\nvector<int> successfulPairs(vector<int>& spells, vector<int>& potions, long long success) {\n    sort(begin(potions), end(potions));\n    for (int i = 0; i < spells.size(); ++i) {\n        long long comp = (success + spells[i] - 1) / spells[i];\n        spells[i] = potions.size() - (lower_bound(begin(potions), end(potions), comp) - begin(potions));\n    }\n    return spells;\n}\n```\n#### Two Pointers\n**C++**\n```cpp\nvector<int> successfulPairs(vector<int>& spells, vector<int>& potions, long long success) {\n    vector<int> idx(spells.size());\n    iota(begin(idx), end(idx), 0);\n    sort(begin(potions), end(potions), greater<int>());\n    sort(begin(idx), end(idx), [&](int i, int j){ return spells[i] < spells[j]; });\n    for (int i = 0, j = 0; i < idx.size(); ++i) {\n        while (j < potions.size() && (long long)potions[j] * spells[idx[i]] >= success)\n            ++j;\n        spells[idx[i]] = j;\n    }\n    return spells;\n}\n```
['C']