# # Added for hot water storage # class Water_storage(Asset): # """Subclass for Asset. # Hot water storage is modeled as follows: # - Rated power is power in MW that battery can # import from and export to the grid # - Efficiency loss is applied at charging, meaning that # SoC increase when charging is lower than the SoC decrease # when discharging # """ # def __init__( # self, # name, # min_capacity, # max_capacity, # power_capex, # capacity_capex, # average_eff, # energy_density, # lifetime, # opex # ): # super().__init__(name=name) # self.min_capacity = min_capacity # self.max_capacity = max_capacity # self.power_capex = power_capex # self.capacity_capex = capacity_capex # self.average_eff = average_eff # self.lifetime = lifetime # self.opex = opex # def __repr__(self): # return ( # f"Battery(self, rated_power={self.max_power}, rated_capacity={self.capacity}, " # f"roundtrip_eff={self.rt_eff}, min_soc={self.min_soc}, max_soc={self.max_soc})" # ) # def get_soc(self): # """Get the SoC in % (decimal value)""" # return self.chargelevel / self.capacity # def set_chargelevel(self, chargelevel): # """Set the chargelevel in MWh. Will automatically change the SoC accordingly.""" # if chargelevel < self.min_chargelevel or chargelevel > self.max_chargelevel: # raise ValueError( # f"Tried to set Charge Level to {chargelevel}. " # f"Charge Level must be a value between " # f"{self.min_chargelevel} and {self.max_chargelevel} (in MWh)" # ) # self.chargelevel = chargelevel # def set_load(self, load): # """Set load of the battery. # Use negative values for charging and positive values for discharging. # Returns actual chargespeed, considering technical limitations of the battery. # Note: We currently assume all efficiency losses occur during charging (no losses during discharge) # """ # if not hasattr(self, "freq"): # raise AttributeError( # "Time frequency of the model is not defined. " # "Assign asset to a CaseStudy or use Asset.freq(). " # "to set de time frequency and try again." # ) # load = super().set_load(load) # unbound_charging = self.MW_to_MWh(load) # if load < 0: # unbound_charging *= self.rt_eff # chargelevel = self.chargelevel # max_charging = chargelevel - self.max_chargelevel # max_discharging = chargelevel - self.min_chargelevel # bound_charging = min(max(unbound_charging, max_charging), max_discharging) # newcl = chargelevel - bound_charging # self.set_chargelevel(newcl) # if bound_charging < 0: # bound_charging /= self.rt_eff # self.cycle_count += abs(bound_charging / (self.capacity * 2)) # return self.MWh_to_MW(bound_charging) # def charge(self, chargespeed): # """Charge the battery with given chargespeed. # Redirects to Battery.set_load(). # Returns load (negative value for charging). # """ # chargespeed = self.max_power if chargespeed == "max" else chargespeed # if chargespeed < 0: # raise ValueError( # f"Chargespeed should be always be a positive value by convention. " # f"Inserted {chargespeed}." # ) # chargespeed = self.set_load(-chargespeed) # return chargespeed # def discharge(self, dischargespeed): # """Discharge the battery by given amount. # Redirects to Battery.set_load(). # Returns load (positive value for discharging). # """ # dischargespeed = self.max_power if dischargespeed == "max" else dischargespeed # if dischargespeed < 0: # raise ValueError( # f"Dischargespeed should be always be a positive value by convention. " # f"Inserted {dischargespeed}." # ) # dischargespeed = self.set_load(dischargespeed) # return dischargespeed