Skip to content

Commit

Permalink
Earliest Second to Mark Indices II
Browse files Browse the repository at this point in the history
  • Loading branch information
hikjik committed Feb 26, 2024
1 parent feb47d6 commit 3e8c598
Show file tree
Hide file tree
Showing 6 changed files with 98 additions and 0 deletions.
1 change: 1 addition & 0 deletions CMakeLists.txt
Original file line number Diff line number Diff line change
Expand Up @@ -418,6 +418,7 @@ add_task(dungeon-game)
add_task(duplicate-zeros)
add_task(earliest-possible-day-of-full-bloom)
add_task(earliest-second-to-mark-indices-i)
add_task(earliest-second-to-mark-indices-ii)
add_task(edit-distance)
add_task(egg-drop-with-2-eggs-and-n-floors)
add_task(element-appearing-more-than-25-in-sorted-array)
Expand Down
1 change: 1 addition & 0 deletions PROBLEM_LIST.md
Original file line number Diff line number Diff line change
Expand Up @@ -1892,3 +1892,4 @@
| 3046. | [Split the Array](https://leetcode.com/problems/split-the-array/) | [C++](./solutions/split-the-array/solution.hpp) | <img src='https://img.shields.io/badge/Easy-darkgreen?style=flat-square'/> | O(N) / O(N)| | |
| 3047. | [Find the Largest Area of Square Inside Two Rectangles](https://leetcode.com/problems/find-the-largest-area-of-square-inside-two-rectangles/) | [C++](./solutions/find-the-largest-area-of-square-inside-two-rectangles/solution.hpp) | <img src='https://img.shields.io/badge/Medium-darkorange?style=flat-square'/> | O(N<sup>2</sup>) / O(1)| | |
| 3048. | [Earliest Second to Mark Indices I](https://leetcode.com/problems/earliest-second-to-mark-indices-i/) | [C++](./solutions/earliest-second-to-mark-indices-i/solution.hpp) | <img src='https://img.shields.io/badge/Medium-darkorange?style=flat-square'/> | O((M+N)logM) / O(N)| | |
| 3049. | [Earliest Second to Mark Indices II](https://leetcode.com/problems/earliest-second-to-mark-indices-ii/) | [C++](./solutions/earliest-second-to-mark-indices-ii/solution.hpp) | <img src='https://img.shields.io/badge/Hard-darkred?style=flat-square'/> | O((NlogN+M)logM) / O(N)| | |
1 change: 1 addition & 0 deletions solutions/earliest-second-to-mark-indices-i/solution.hpp
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
#pragma once

#include <ranges>
#include <vector>

// Time: O((M+N)logM)
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
add_catch(test_earliest_second_to_mark_indices_ii test.cpp)
59 changes: 59 additions & 0 deletions solutions/earliest-second-to-mark-indices-ii/solution.hpp
Original file line number Diff line number Diff line change
@@ -0,0 +1,59 @@
#pragma once

#include <numeric>
#include <queue>
#include <ranges>
#include <vector>

// Time: O((NlogN+M)logM)
// Space: O(N)

class Solution {
public:
static int
earliestSecondToMarkIndices(const std::vector<int> &nums,
const std::vector<int> &changeIndices) {
const int m = changeIndices.size();
int left = 1, right = m + 1;
while (left < right) {
const auto middle = left + (right - left) / 2;
canMark(nums, changeIndices, middle) ? right = middle : left = middle + 1;
}
return left == m + 1 ? -1 : left;
}

private:
static bool canMark(const std::vector<int> &nums,
const std::vector<int> &changeIndices, int m) {
std::vector<int> first(nums.size(), -1);
for (int i = m - 1; i >= 0; --i) {
if (nums[changeIndices[i] - 1]) {
first[changeIndices[i] - 1] = i;
}
}

std::priority_queue<int, std::vector<int>, std::greater<>> minHeap;
int ops = 0;
for (int i = m - 1; i >= 0; --i) {
if (i == first[changeIndices[i] - 1]) {
minHeap.push(nums[changeIndices[i] - 1]);
if (ops) {
--ops;
} else {
++ops;
minHeap.pop();
}
} else {
++ops;
}
}

long long sum = std::reduce(nums.begin(), nums.end(), 0LL) + nums.size() -
minHeap.size();
while (!minHeap.empty()) {
sum -= minHeap.top();
minHeap.pop();
}
return sum <= ops;
}
};
35 changes: 35 additions & 0 deletions solutions/earliest-second-to-mark-indices-ii/test.cpp
Original file line number Diff line number Diff line change
@@ -0,0 +1,35 @@
#include <catch.hpp>

#include <solution.hpp>

TEST_CASE("Simple") {
struct TestCase {
std::vector<int> nums;
std::vector<int> changeIndices;
int expected;
};

std::vector<TestCase> test_cases{
{
.nums{0, 0, 1, 2},
.changeIndices{1, 2, 1, 2, 1, 2, 1, 2},
.expected = 7,
},
{
.nums{3, 2, 3},
.changeIndices{1, 3, 2, 2, 2, 2, 3},
.expected = 6,
},
{
.nums{1, 2, 3},
.changeIndices{1, 2, 3},
.expected = -1,
},
};

for (const auto &[nums, changeIndices, expected] : test_cases) {
const auto actual =
Solution::earliestSecondToMarkIndices(nums, changeIndices);
REQUIRE(expected == actual);
}
}

0 comments on commit 3e8c598

Please sign in to comment.