From a3819c9b265e67ea3a1e27a7d95f91f93586e228 Mon Sep 17 00:00:00 2001 From: Dan Buch Date: Sat, 21 Oct 2023 07:18:56 -0400 Subject: [PATCH] A poorly-made min stack --- leetcode/stuff.py | 24 +++++++++++++++++++++ leetcode/test_stuff.py | 49 ++++++++++++++++++++++++++++++++++++++++++ 2 files changed, 73 insertions(+) diff --git a/leetcode/stuff.py b/leetcode/stuff.py index c6682c1..0525b95 100644 --- a/leetcode/stuff.py +++ b/leetcode/stuff.py @@ -138,3 +138,27 @@ class Roman: total += cls.ALL[c] return total + + +class MinStack: + def __init__(self): + self._v: list[int] = [] + self._min: int | None = None + + def push(self, val: int) -> None: + self._v.append(val) + + if self._min is None or self._min > val: + self._min = val + + def pop(self) -> None: + popped = self._v.pop(-1) + + if popped == self._min: + self._min = min(self._v) + + def top(self) -> int: + return self._v[-1] + + def getMin(self) -> int: # no qa + return typing.cast(int, self._min) diff --git a/leetcode/test_stuff.py b/leetcode/test_stuff.py index 6238589..87418a6 100644 --- a/leetcode/test_stuff.py +++ b/leetcode/test_stuff.py @@ -28,3 +28,52 @@ def test_find_sqrt_ish(n: int, expected: int): ) def test_int_to_roman(n: int, expected: str): assert stuff.Roman.i2r(n) == expected + + +@pytest.mark.parametrize( + ("ops", "expected"), + [ + ( + ( + [ + ("new",), + ("push", -2), + ("push", 0), + ("push", -3), + ("getMin",), + ("pop",), + ("top",), + ("getMin",), + ] + ), + [ + None, + None, + None, + None, + -3, + None, + 0, + -2, + ], + ) + ], +) +def test_min_stack(ops: list[tuple[str] | tuple[str, int]], expected: list[int | None]): + returned: list[int | None] = [] + inst: stuff.MinStack | None = None + + for op in ops: + if len(op) == 1: + if op[0] == "new": + inst = stuff.MinStack() + returned.append(None) + continue + + returned.append(getattr(inst, op[0])()) + continue + + method, arg = op + returned.append(getattr(inst, method)(arg)) + + assert returned == expected