Skip to content

Commit 9702903

Browse files
Implement Trapped RainWater (#2716)
* chore: add `trapped_rainwater.cpp` to DIRECTORY.md * feat: implement Trapped Rain Water algorithm * chore: add links to the trapped rain water problem * chore(docs): remove Trapped Rain Water dir * ref: add edges tests * doc: adding Sozel as author * doc: includes documentatino * ref: use `unsigned int` for height of walls * fix: use fixed-width integers instead of unsigned int * chore: rearrange included libraries --------- Co-authored-by: realstealthninja <[email protected]>
1 parent 1d69222 commit 9702903

File tree

1 file changed

+104
-0
lines changed

1 file changed

+104
-0
lines changed
+104
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,104 @@
1+
/**
2+
* @file
3+
* @brief Implementation of the [Trapped Rainwater
4+
* Problem](https://www.geeksforgeeks.org/trapping-rain-water/)
5+
* @details
6+
* This implementation calculates the amount of rainwater that can be trapped
7+
* between walls represented by an array of heights.
8+
* @author [SOZEL](https://github.com/TruongNhanNguyen)
9+
*/
10+
11+
#include <algorithm> /// For std::min and std::max
12+
#include <cassert> /// For assert
13+
#include <cstddef> /// For std::size_t
14+
#include <cstdint> /// For integral typedefs
15+
#include <vector> /// For std::vector
16+
17+
/*
18+
* @namespace
19+
* @brief Dynamic Programming Algorithms
20+
*/
21+
namespace dynamic_programming {
22+
/**
23+
* @brief Function to calculate the trapped rainwater
24+
* @param heights Array representing the heights of walls
25+
* @return The amount of trapped rainwater
26+
*/
27+
uint32_t trappedRainwater(const std::vector<uint32_t>& heights) {
28+
std::size_t n = heights.size();
29+
if (n <= 2)
30+
return 0; // No water can be trapped with less than 3 walls
31+
32+
std::vector<uint32_t> leftMax(n), rightMax(n);
33+
34+
// Calculate the maximum height of wall to the left of each wall
35+
leftMax[0] = heights[0];
36+
for (std::size_t i = 1; i < n; ++i) {
37+
leftMax[i] = std::max(leftMax[i - 1], heights[i]);
38+
}
39+
40+
// Calculate the maximum height of wall to the right of each wall
41+
rightMax[n - 1] = heights[n - 1];
42+
for (std::size_t i = n - 2; i < n; --i) {
43+
rightMax[i] = std::max(rightMax[i + 1], heights[i]);
44+
}
45+
46+
// Calculate the trapped rainwater between walls
47+
uint32_t trappedWater = 0;
48+
for (std::size_t i = 0; i < n; ++i) {
49+
trappedWater +=
50+
std::max(0u, std::min(leftMax[i], rightMax[i]) - heights[i]);
51+
}
52+
53+
return trappedWater;
54+
}
55+
56+
} // namespace dynamic_programming
57+
58+
/**
59+
* @brief Self-test implementations
60+
* @returns void
61+
*/
62+
static void test() {
63+
std::vector<uint32_t> test_basic = {0, 1, 0, 2, 1, 0, 1, 3, 2, 1, 2, 1};
64+
assert(dynamic_programming::trappedRainwater(test_basic) == 6);
65+
66+
std::vector<uint32_t> test_peak_under_water = {3, 0, 2, 0, 4};
67+
assert(dynamic_programming::trappedRainwater(test_peak_under_water) == 7);
68+
69+
std::vector<uint32_t> test_bucket = {5, 1, 5};
70+
assert(dynamic_programming::trappedRainwater(test_bucket) == 4);
71+
72+
std::vector<uint32_t> test_skewed_bucket = {4, 1, 5};
73+
assert(dynamic_programming::trappedRainwater(test_skewed_bucket) == 3);
74+
75+
std::vector<uint32_t> test_empty = {};
76+
assert(dynamic_programming::trappedRainwater(test_empty) == 0);
77+
78+
std::vector<uint32_t> test_flat = {0, 0, 0, 0, 0};
79+
assert(dynamic_programming::trappedRainwater(test_flat) == 0);
80+
81+
std::vector<uint32_t> test_no_trapped_water = {1, 1, 2, 4, 0, 0, 0};
82+
assert(dynamic_programming::trappedRainwater(test_no_trapped_water) == 0);
83+
84+
std::vector<uint32_t> test_single_elevation = {5};
85+
assert(dynamic_programming::trappedRainwater(test_single_elevation) == 0);
86+
87+
std::vector<uint32_t> test_two_point_elevation = {5, 1};
88+
assert(dynamic_programming::trappedRainwater(test_two_point_elevation) ==
89+
0);
90+
91+
std::vector<uint32_t> test_large_elevation_map_difference = {5, 1, 6, 1,
92+
7, 1, 8};
93+
assert(dynamic_programming::trappedRainwater(
94+
test_large_elevation_map_difference) == 15);
95+
}
96+
97+
/**
98+
* @brief Main function
99+
* @returns 0 on exit
100+
*/
101+
int main() {
102+
test(); // run self-test implementations
103+
return 0;
104+
}

0 commit comments

Comments
 (0)