X-Git-Url: https://wannabe.guru.org/gitweb/?a=blobdiff_plain;f=src%2Fpyutils%2Fmath_utils.py;h=2270364ed6521e341b713418b71be313a0732a57;hb=cb25f35595b220b0573170954183d6c296d511e5;hp=dd8f33a2e4bf781b658d4ae7266e4a3035412dbb;hpb=985dfef399576a0db52c158931c3afd273e96842;p=pyutils.git diff --git a/src/pyutils/math_utils.py b/src/pyutils/math_utils.py index dd8f33a..2270364 100644 --- a/src/pyutils/math_utils.py +++ b/src/pyutils/math_utils.py @@ -11,10 +11,11 @@ from heapq import heappop, heappush from typing import Dict, List, Optional, Tuple from pyutils import dict_utils +from pyutils.types.simple import Numeric class NumericPopulation(object): - """This object *store* a numerical population in a way that enables relatively + """This object *store* a numeric population in a way that enables relatively fast addition of new numbers (:math:`O(2log_2 n)`) and instant access to the median value in the population (:math:`O(1)`). It also provides other population summary statistics such as the :meth:`get_mode`, :meth:`get_percentile` and @@ -50,11 +51,11 @@ class NumericPopulation(object): def __init__(self): self.lowers, self.highers = [], [] self.aggregate = 0.0 - self.sorted_copy: Optional[List[float]] = None + self.sorted_copy: Optional[List[Numeric]] = None self.maximum = None self.minimum = None - def add_number(self, number: float): + def add_number(self, number: Numeric): """Adds a number to the population. Runtime complexity of this operation is :math:`O(2 log_2 n)` @@ -92,7 +93,7 @@ class NumericPopulation(object): elif len(self.highers) - len(self.lowers) > 1: heappush(self.lowers, -heappop(self.highers)) - def get_median(self) -> float: + def get_median(self) -> Numeric: """ Returns: The median (p50) of the current population in :math:`O(1)` time. @@ -112,13 +113,13 @@ class NumericPopulation(object): count = len(self) return self.aggregate / count - def get_mode(self) -> Tuple[float, int]: + def get_mode(self) -> Tuple[Numeric, int]: """ Returns: The population mode (most common member in the population) in :math:`O(n)` time. """ - count: Dict[float, int] = collections.defaultdict(int) + count: Dict[Numeric, int] = collections.defaultdict(int) for n in self.lowers: count[-n] += 1 for n in self.highers: @@ -150,7 +151,7 @@ class NumericPopulation(object): self.sorted_copy.append(x) self.sorted_copy = sorted(self.sorted_copy) - def get_percentile(self, n: float) -> float: + def get_percentile(self, n: float) -> Numeric: """ Returns: the number at approximately pn% in the population (i.e. the nth percentile) in :math:`O(n log_2 n)` time (it