import math """ Energy - General functions """ multipliers = { 'Y': 1e24, 'Z': 1e21, 'E': 1e18, 'P': 1e15, 'T': 1e12, 'G': 1e9, 'M': 1e6, 'K': 1e3, 'x': 1.0, 'm': 1e-3, 'u': 1e-6, 'n': 1e-9, 'p': 1e-12, 'f': 1e-15, 'a': 1e-18, 'z': 1e-21, 'y': 1e-24, } mult_pow = { 24: 'Y', 21: 'Z', 18: 'E', 15: 'P', 12: 'T', 9: 'G', 6: 'M', 3: 'K', 0: '', -3: 'm', -6: 'u', -9: 'n', -12: 'p', -15: 'f', -18: 'a', -21: 'z', -24: 'y', } def float_to_str(value, round_val=None, omit_dot_zero=False): sign = '' if value < 0: sign = '-' value = -1 * value target_mult = 0 if value == 0: return "0" elif value < 1: while value < 1: target_mult -= 3 value = value * 1000.0 else: while value >= 1000: target_mult += 3 value = value / 1000.0 if round_val is not None: value = round(value, round_val) if omit_dot_zero and value.is_integer(): value = int(value) return f"{sign}{value}{mult_pow[target_mult]}" def str_to_float(value): """ Converts a string to a float, accounting for unit multipliers such as M/k/m/u """ multiplier = str(value)[-1] # account for multiplier if multiplier in multipliers: number = float(value[:-1]) multiplier = float(multipliers[multiplier]) value = number * multiplier return float(value) def str_to_int(value): """ Converts a string to an int, accounting for unit multipliers such as M/k/m/u """ float_value = str_to_float(value) return int(float_value) def str_add_vals(val1, val2): """ Adds two values in str representation :param val1: first value (with unit multipliers) :param val2: second value (with unit multipliers) :return: the sum in textual representation (with unit multipliers) """ mul1 = str(val1[-1]) mul2 = str(val2[-1]) if mul1 not in multipliers: val1 = f"{val1}x" mul1 = "x" if mul2 not in multipliers: val2 = f"{val2}x" mul2 = "x" # equal multiplier -> sum vals if mul1 == mul2: number = float(val1[:-1]) + float(val2[:-1]) else: # Invert numbers so that mul1 < mul2 if multipliers[mul1] > multipliers[mul2]: mul1, mul2 = mul2, mul1 val1, val2 = val2, val1 # mul1 < mul2 -> calculate multiplication ratio ratio = multipliers[mul2]/multipliers[mul1] number = float(val1[:-1]) + float(val2[:-1]) * ratio if '.' not in str(val1) and '.' not in str(val2): number = int(number) return f"{number}{mul1 if mul1 != 'x' else ''}" def energy_from_I_t(V, I, t): """ Calculates the energy consumption in the time interval t :param V: voltage :param I: current draw :param t: time interval """ return float(V) * float(I) * float(t) def energy_from_R_t(V, R, t): """ Calculates the energy consumption in the time interval t :param V: voltage :param R: resistance :param t: time interval """ return float(V) * (float(V) / float(R)) * float(t) def energy_from_I_f(V, I, f): """ Calculates the energy consumption of a clock cycle with frequency f :param V: voltage :param I: current draw :param f: clock frequency """ return float(V) * float(I) / float(f) def energy_from_R_f(V, R, f): """ Calculates the energy consumption of a clock cycle with frequency f :param V: voltage :param R: resistance :param f: clock frequency """ return float(V) * (float(V) / float(R) ) / float(f) def equivalent_resistance(V, I): """ Calculates the equivalent resistance of a given voltage and current draw :param V: Voltage (V) :param I: Current Draw (A) """ i = str_to_float(I) v = str_to_float(V) r = v / i return r def R_from_energy_t(V, e, t): """ Calculates the instantaneous equivalent resistance given the energy consumption in an instant t under the voltage V :param V: Voltage (V) :param e: energy consumed in t :param t: time interval :return: the equivalent resistance """ # e = V * I * t -> I = e / (V * t) # V = R * I -> R = V / I # R = V / (e / (V * t)) = V * V * t / e if e == 0.0: return float('inf') r = (V * V * t) / e return r def R_from_parallel_r(R1, R2): """ Calculates the equivalent resistance of two parallel resistors :param R1: resistor 1 :param R2: resistor 2 :return: the equivalent resistance """ if R1 == 0.0: return R2 elif R2 == 0.0: return R1 return 1.0 / (1.0 / R1 + 1.0 / R2) def P_R_to_V(P, R): """ Calculates the voltage from instantaneous power and equivalent resistance :param P: power :param R: resistance """ # P = I * V # V = R * I; I = V / R; # P = (V * V) / R # V = SQRT(P * R) return math.sqrt(P*R)