def kennfeld_simulieren(mp, Root_simulationsergebnisse, model_kennfeld_path, model_kennfeld_name): dymola = None try: #erzeuge Instanz von Dymola dymola = DymolaInterface() print(model_kennfeld_path, model_kennfeld_name) #öffne das Model dymola.openModel(path=model_kennfeld_path) dymola.translateModel(problem=model_kennfeld_name) print('simulieren') result = dymola.simulateExtendedModel( problem=model_kennfeld_name, stopTime=200000, method='radau IIa', resultFile=Root_simulationsergebnisse + '\simulationsergebnis_mp' + str(mp)) print(result[0]) if not result: print("Simulation failed. Below is the translation log.") log = dymola.getLastError() print(log) except DymolaException as ex: print("Error: " + str(ex)) if dymola is not None: dymola.close() dymola = None return
def simulator(self): try: dymola = None dymola = DymolaInterface("C:/Program Files/Dymola 2019 FD01/bin64/Dymola.exe") openResult = dymola.openModel(self.packageName) print(" openModel : ", openResult ) if not openResult: print("openModel is failed. Below is the translation log.") log = dymola.getLastErrorLog() print(log) exit(1) dymola.experimentSetupOutput(events=False) result = dymola.simulateExtendedModel(self.modelName,0.0, self.simTime, 0, self.deltaTime, "Radau", 0.00001, self.deltaTime, self.resultName, initialNames=self.handleModelParamName, initialValues=self.handleModelParamVal) print(" simulateExtendedModel : ", result[0]) if not result[0]: print("Simulation is failed. Below is the translation log.") log = dymola.getLastErrorLog() print(log) exit(1) except DymolaException as ex: print(("Error: " + str(ex))) finally: if dymola is not None: dymola.close() dymola = None return 0
def simulate_optimal(ladephasen, entladephasen, simulationsdauer, dir_laden_daten, dir_modell_sim, name_modell_sim, Root_simulationsergebnisse): ladephasen = clear_phasen(ladephasen) entladephasen = clear_phasen(entladephasen) input_laden = merge(ladephasen, dir_laden_daten) input_entladen = merge(entladephasen, dir_laden_daten) try: #erzeuge Instanz von Dymola dymola = DymolaInterface() dymola.openModel(path=dir_modell_sim) dymola.translateModel(problem=name_modell_sim) dymola.ExecuteCommand("laden.table=" + input_laden) dymola.ExecuteCommand("entladen.table=" + input_entladen) result = dymola.simulateExtendedModel(problem=name_modell_sim, stopTime=simulationsdauer * 3600, method='radau IIa', finalNames=['Stromkosten.y'], resultFile=os.path.join( Root_simulationsergebnisse, 'simulation_optimal')) print(result[0]) Stromkosten = result[1] print('optimale Stromkosten', Stromkosten[0]) if not result: print("Simulation failed. Below is the translation log.") log = dymola.getLastError() print(log) dymola.plot(["elektrische_leistungsaufnahme.y"]) dymola.ExportPlotAsImage( os.path.join(Root_simulationsergebnisse, "Leistungsaufnahme_optimal.png")) dymola.plot(["__ctt__strompreis.y[1]"]) dymola.ExportPlotAsImage( os.path.join(Root_simulationsergebnisse, "Strompreis.png")) dymola.plot(["cost_calculation1.out_kkm1_drehzahl_min_unterschritten"]) dymola.ExportPlotAsImage( os.path.join(Root_simulationsergebnisse, "Drehzahl_unterschritten.png")) dymola.plot(["cost_calculation1.out_Investitionskosten_kkm1"]) dymola.ExportPlotAsImage( os.path.join(Root_simulationsergebnisse, "Invest_KKM.png")) dymola.plot(["cost_calculation1.out_Investitionskosten_Speicher"]) dymola.ExportPlotAsImage( os.path.join(Root_simulationsergebnisse, "Invest_Speicher.png")) except DymolaException as ex: print("Error: " + str(ex)) if dymola is not None: dymola.close() dymola = None return input_laden, input_entladen, ladephasen, entladephasen
def simulation(paths, models, times, A, t, htc, modelon, lcl, dir_save): modelon = modelon lcl = lcl A = A t = t htc = htc dir_save = dir_save for pat, model, time in zip(paths, models, times): dymola = None try: # Instantiate the Dymola interface and start Dymola dymola = DymolaInterface() # Loading libs dymola.openModel(path=modelon) dymola.openModel(path=lcl) # Load model dymola.openModel(path=pat) dymola.translateModel(model) # Call a function in Dymola and check its return value result = dymola.simulateExtendedModel( problem=model, startTime=0, stopTime=time, outputInterval=0.5, method="Esdirk45a", initialNames=["A", "T", "htc"], initialValues=[A, t, htc], resultFile=dir_save + "\\" + model) # result = dymola.simulateModel("C_Two_M_and_I", startTime=0, stopTime=t_stop, resultFile=dir_path + "_result") if not result: print("Simulation failed. Below is the translation log.") log = dymola.getLastErrorLog() print(log) # dymola.plot(["MotorStator.T", "Inverter_Al.T"], legends=['T_motor', 'T_inverter']) # dymola.ExportPlotAsImage(r'C:\Users\sanjio.durasevic\Desktop\C2\12_11_2018_Motor_Inverter_script\plots\slika.png') except DymolaException as ex: print("Error: " + str(ex)) finally: if dymola is not None: dymola.close() dymola = None
def simulate(): dir_aixlib = r"D:\Sciebo\Programmierung\GIT\_Standard\AixLib\AixLib" dir_result = r"D:\Sciebo\Programmierung\Tests\Dymola" dymola = DymolaInterface() try: dymola.openModel(path=os.path.join(dir_aixlib, 'package.mo')) # dymola.openModel(r"D:\Sciebo\Programmierung\Tests\Dymola\Test_BUDO.mo") dymola.translateModel( 'AixLib.Fluid.BoilerCHP.Examples.Test_BUDO.CompleteModel') output = dymola.simulateExtendedModel( problem='AixLib.Fluid.BoilerCHP.Examples.Test_BUDO.CompleteModel', startTime=0.0, stopTime=86400, outputInterval=500, method="Dassl", tolerance=0.0001, resultFile=os.path.join(dir_result, 'demo_results'), finalNames=['boiler_system.temperature_sensor_2.T'], ) print(output[1]) error = dymola.getLastError() print(error) # dymola.plot( # ["boiler_system.temperature_sensor_2.T", "combiTimeTable.y[3]"]) # dymola.ExportPlotAsImage(os.path.join(dir_result, "plot.png")) # list_var = dymola.list( # r"D:\Sciebo\Programmierung\Tests\Dymola\Test_BUDO.txt", variables='*"H02.1"*') # print(list_var) # list_var = dymola.variables( # r"D:\Sciebo\Programmierung\Tests\Dymola\Test_BUDO.txt") # print(list_var) # list_var = dymola.getExperiment() # print(list_var) # list_var = dymola.listfunctions(filter="*") # print(list_var) dymola.exit() except: print("Unexpected error:", sys.exc_info()) dymola.exit()
def createDymosimExe(modelPath, stopTime): dymola = None try: dymola = DymolaInterface() result = dymola.simulateExtendedModel(modelPath, 0.0, stopTime, 0, 0.0, "Dassl", 0.0001, 0.0, None, None, None, ["Result"], True) print(result) if not result[0]: print("Simulation failed. Below is the translation log.") log = dymola.getLastErrorLog() print(log) except DymolaException as ex: print(("Error: " + str(ex))) finally: if dymola is not None: dymola.close() dymola = None
def simulate_compare(simulationsdauer, dir_modell_sim, name_modell_sim, Root_simulationsergebnisse): try: #erzeuge Instanz von Dymola dymola = DymolaInterface() dymola.openModel(path=dir_modell_sim) dymola.translateModel(problem=name_modell_sim) result = dymola.simulateExtendedModel(problem=name_modell_sim, stopTime=simulationsdauer * 3600, method='radau IIa', finalNames=['Stromkosten.y'], resultFile=os.path.join( Root_simulationsergebnisse, 'simulation_optimal')) print(result[0]) Stromkosten = result[1] #ergebnis[step-1,1]=Stromkosten[0]☺ print('Vergleichs-Stromkosten', Stromkosten[0]) if not result: print("Simulation failed. Below is the translation log.") log = dymola.getLastError() print(log) dymola.plot(["elektrische_leistungsaufnahme.y"]) dymola.ExportPlotAsImage( os.path.join(Root_simulationsergebnisse, "vergleichs_ergebnis.png")) except DymolaException as ex: print("Error: " + str(ex)) if dymola is not None: dymola.close() dymola = None return Stromkosten
def simulate_flex(model_name, model_path, sim_duration, flex_var, param_dict): dymola = DymolaInterface() #Model muss noch geöffnet sein openModel = dymola.openModel(path=model_path) print(openModel) translateModel = dymola.translateModel(problem=model_name) print(translateModel) if flex_var == 1: #erste Ebene dymola.ExecuteCommand("konf_Bivalenz=true") dymola.ExecuteCommand("konf_HK=true") dymola.ExecuteCommand("konf_BHKW_stromgefuehrt=false") #zweite Ebene dymola.ExecuteCommand(str("konf_BHKW=" + param_dict["konf_BHKW"])) dymola.ExecuteCommand(str("konf_WRG=" + param_dict["konf_WRG"])) dymola.ExecuteCommand(str("konf_Puffer=" + param_dict["konf_Puffer"])) dymola.ExecuteCommand(str("Anzahl_HK=" + param_dict["Anzahl_HK"])) #die if-Bedingung ist nur zur Sicherheit if param_dict["konf_WRG"] == "true": dymola.ExecuteCommand(str("Anzahl_WRG=" + param_dict["Anzahl_WRG"])) else: dymola.ExecuteCommand("Anzahl_WRG=0") elif flex_var == 2: #erste Ebene dymola.ExecuteCommand("konf_BHKW=true") dymola.ExecuteCommand("konf_Bivalenz=false") dymola.ExecuteCommand("konf_BHKW_Puffer=true") dymola.ExecuteCommand("konf_BHKW_stromgefuehrt=true") #zweite Ebene dymola.ExecuteCommand(str("konf_HK=" + param_dict["konf_HK"])) dymola.ExecuteCommand(str("konf_WRG=" + param_dict["konf_WRG"])) #die if-Bedingung ist nur zur Sicherheit if param_dict["konf_HK"] == "true": dymola.ExecuteCommand(str("Anzahl_HK=" + param_dict["Anzahl_HK"])) else: dymola.ExecuteCommand("Anzahl_HK=0") #die if-Bedingung ist nur zur Sicherheit if param_dict["konf_WRG"] == "true": dymola.ExecuteCommand(str("Anzahl_WRG=" + param_dict["Anzahl_WRG"])) else: dymola.ExecuteCommand("Anzahl_WRG=0") else: print("Auswahl der Flexibilisierungsmaßnahme fehlerhaft") result = dymola.simulateExtendedModel(problem=model_name, stopTime=sim_duration, finalNames=[ "konf_Bivalenz", "konf_HK", "konf_BHKW_stromgefuehrt", "konf_BHKW", "konf_WRG", "konf_Puffer", "Anzahl_WRG", "Anzahl_HK" ]) if not result[0]: print("Simulation failed. Below is the translation log.") log = dymola.getLastError() print(log) print('ERGEBNIS_Inhalt:', "konf_Bivalenz", "konf_HK", "konf_BHKW_stromgefuehrt", "konf_BHKW", "konf_WRG", "konf_Puffer", "Anzahl_WRG", "Anzahl_HK") #saveModel=dymola.saveTotalModel('C:/Users/theisinger_l/waerme_save.mo', "waerme") #Achtung Dymola speichert mit saveTotalModel anscheinend nicht parameterwerte ab.. #print(saveModel) dymola.close() return result
class DymolaBaseEnv(gym.Env): """ A variation of the ModelicaGym FMU interface that uses the Dymola API. To install dymola API add dymola.exe to the system PATH variable. """ def __init__(self): """ :param model_path: path to the model FMU. Absolute path is advised. :param mode: FMU exporting mode "CS" or "ME" :param config: dictionary with model specifications: model_input_names - names of parameters to be used as action. model_output_names - names of parameters to be used as state descriptors. model_parameters - dictionary of initial parameters of the model time_step - time difference between simulation steps positive_reward - (optional) positive reward for default reward policy. Is returned when episode goes on. negative_reward - (optional) negative reward for default reward policy. Is returned when episode is ended :param log_level: level of logging to be used """ with open(self.conf_file) as f: config = json.load(f) logger.setLevel(config['log_level']) self.model_name = config['mo_name'] self.dymola = None self.libs = config['libs'] self.reset_dymola() # Parameters required by this implementation self.tau = config['time_step'] self.model_input_names = [] for i in range(len(config['action_names'])): if config['action_len'][i] <= 1: self.model_input_names += [config['action_names'][i]] else: self.model_input_names += [ f"{config['action_names'][i]}[{x}]" for x in range(1, 1 + config['action_len'][i]) ] self.model_output_names = config['state_names'] self.model_parameters = config['model_parameters'] self.default_action = config['default_action'] self.add_names = config['additional_debug_states'] self.method = config['method'] self.negative_reward = config['negative_reward'] self.positive_reward = config['positive_reward'] if not len(self.model_input_names) == len(self.default_action): raise Exception( "The number of action names and the default action values should be the same length." ) # initialize the model time and state self.start = 0 self.stop = self.tau self.done = False self.state = self.reset() # OpenAI Gym requirements self.action_space = self._get_action_space() self.observation_space = self._get_observation_space() self.debug_data = {name: [] for name in self.model_output_names} self.rbc_action_names = [] for i in range(len(config['rbc_action_names'])): if config['rbc_action_len'][i] <= 1: self.rbc_action_names += [config['rbc_action_names'][i]] else: foo = config['rbc_action_names'][i] bar = config['rbc_action_len'][i] self.rbc_action_names += [ f"{foo}[{x}]" for x in range(1, 1 + bar) ] self.rbc_action = [] self.data = None self.tracker = 0 self.exception_flag = False # OpenAI Gym API def render(self, **kwargs): """ OpenAI Gym API. Determines how current environment state should be rendered. :param kwargs: :return: implementation should return rendering result """ pass def reset(self): """ OpenAI Gym API. Determines restart procedure of the environment :return: environment state after restart """ logger.info( "Resetting the environment and deleting old results files.") if os.path.isdir('temp_dir'): # print("Removing old files...") for file in os.listdir('temp_dir'): try: os.remove(os.path.join(os.getcwd(), 'temp_dir', file)) except: pass self.action = self.default_action self.start = 0 self.stop = self.tau logger.info("The model is being reset") res = self.dymola.simulateExtendedModel( self.model_name, startTime=self.start, stopTime=self.stop, initialNames=self.model_input_names, initialValues=self.action, finalNames=self.model_output_names) self.state = res[1] self.cached_values = None self.cached_state = None self.debug_data = { name: [] for name in self.model_output_names + self.add_names } self.state = self.postprocess_state(self.state) self.done = not (res[0]) if self.done: logger.error( f"Model failed to reset. Dymola simulation from time {self.start} to {self.stop} failed with error message: {self.dymola.getLastError()}" ) return flatten(self.state) def reset_dymola(self): if self.dymola: # this doesn't really seem to be working. It hangs self.dymola.close() self.dymola = DymolaInterface() self.dymola.ExecuteCommand("Advanced.Define.DAEsolver = true") # load libraries loaded = [] #self.dymola.eraseClasses('Modelica') for lib in self.libs: # all paths relative to the cwd loaded += [self.dymola.openModel(lib, changeDirectory=False)] if not loaded[-1]: logger.error(f"Could not find library {lib}") if not False in loaded: logger.debug("Successfully loaded all libraries.") if not os.path.isdir('temp_dir'): os.mkdir('temp_dir') self.temp_dir = os.path.join(os.getcwd(), "temp_dir") self.dymola.cd('temp_dir') logger.debug("Dymola has been reset") return def step(self, action): """ OpenAI Gym API. Determines how one simulation step is performed for the environment. Simulation step is execution of the given action in a current state of the environment. :param action: action to be executed. :return: resulting state """ logger.debug("Experiment next step was called.") if self.done: logger.warning( """You are calling 'step()' even though this environment has already returned done = True. You should always call 'reset' once you receive 'done = True' -- any further steps are undefined behavior.""") return np.array(self.state), self.negative_reward, self.done, {} # check if action is a list. If not - create list of length 1 try: iter(action) except TypeError: action = [action] logger.warning( "Model input values (action) should be passed as a list") # Check if number of model inputs equals number of values passed if len(action) != len(list(self.model_input_names)): message = "List of values for model inputs should be of the length {}," \ "equal to the number of model inputs. Actual length {}".format( len(list(self.model_input_names)), len(action)) logger.error(message) raise ValueError(message) # Set input values of the model logger.debug("model input: {}, values: {}".format( self.model_input_names, action)) try: self.done, state = self.do_simulation() self.state = state self.start += self.tau self.stop += self.tau except: print("exception") self.reset() self.exception_flag = True return flatten(self.state), self._reward_policy(), self.done, {} # logging def get_log_file_name(self): log_date = datetime.datetime.utcnow() log_file_name = "{}-{}-{}_{}.txt".format(log_date.year, log_date.month, log_date.day, self.model_name) return log_file_name # internal logic def _get_action_space(self): """ Returns action space according to OpenAI Gym API requirements. :return: one of gym.spaces classes that describes action space according to environment specifications. """ low = -1 * np.ones(len(self.model_input_names)) high = 1 * np.ones(len(self.model_input_names)) return spaces.Box(low, high) def _get_observation_space(self): """ Returns state space according to OpenAI Gym API requirements. :return: one of gym.spaces classes that describes state space according to environment specifications. """ low = -1 * np.ones(len(self.model_output_names)) high = 1 * np.ones(len(self.model_output_names)) return spaces.Box(low, high) def _is_done(self, results): """ Determines logic when experiment is considered to be done. :return: boolean flag if current state of the environment indicates that experiment has ended. """ return not results[0] def do_simulation(self): """ Executes simulation by FMU in the time interval [start_time; stop_time] currently saved in the environment. :return: resulting state of the environment. """ #print("============================") logger.debug("Simulation started for time interval {}-{}".format( self.start, self.stop)) self.act = self.action + self.rbc_action #self.debug_points[-1*self.n_points:] found = self.dymola.importInitialResult('dsres.mat', atTime=self.start) print(found) x = self.dymola.simulateExtendedModel( self.model_name, startTime=self.start, stopTime=self.stop, initialNames=self.model_input_names + self.rbc_action_names, initialValues=self.act, finalNames=self.model_output_names) finished, state = x if finished == False: print('finished = False') print(self.dymola.getLastError()) state = self.reset() finished = True self.get_state_values() logger.debug("Simulation results: {}".format(state)) return not finished, state def _reward_policy(self): """ Determines reward based on the current environment state. By default, implements simple logic of penalizing for experiment end and rewarding each step. :return: reward associated with the current state """ if self.exception_flag: self.exception_flag = False if self.done: reward = self.negative_reward else: reward = self.positive_reward return reward def get_state_values(self): """ Extracts the values of model outputs at the end of modeling time interval from simulation result :return: Values of model outputs as tuple in order specified in `model_outputs` attribute """ self.data = DyMat.DyMatFile('temp_dir/dsres.mat') for name in self.debug_data: self.debug_data[name] += self.data[name].tolist() for name in self.add_names + self.model_input_names + self.rbc_action_names: if not name in self.debug_data: self.debug_data.update({name: []}) self.debug_data[name] += self.data[name].tolist() return def _set_init_parameter(self): """ Sets initial parameters of a model. :return: environment """ if self.model_parameters is not None: self.model.set(list(self.model_parameters), list(self.model_parameters.values())) return self
import os # Import dymola package from dymola.dymola_interface import DymolaInterface # Start the interface dymola = DymolaInterface() # Location of your local AixLib clone dir_aixlib = r"C:\Users\hinack\Dropbox\09_Modelica_Library\AixLib" # Location where to store the results dir_result = r"C:\Users\hinack\Dropbox\18_ModelManagement" # Open AixLib dymola.openModel(path=os.path.join(dir_aixlib, 'package.mo')) # Translate any model you'd like to simulate dymola.translateModel('AixLib.ThermalZones.ReducedOrder.Examples.ThermalZone') # Simulate the model output = dymola.simulateExtendedModel( problem='AixLib.ThermalZones.ReducedOrder.Examples.ThermalZone', startTime=0.0, stopTime=3.1536e+07, outputInterval=3600, method="Dassl", tolerance=0.0001, resultFile=os.path.join(dir_result, 'demo_results'), finalNames=['thermalZone.TAir'], ) dymola.close()
def optimierung(liste_minima, liste_maxima, liste_ladephasen, array_names, simulationsdauer, dir_laden_daten, dir_modell_sim, name_modell_sim, Root_simulationsergebnisse, ergebnis_compare): Zyklenanzahl = len(liste_ladephasen) Zyklus = 1 liste_entladephasen = np.zeros(np.shape(liste_ladephasen)) #ein Zyklus bedeutet die Zeitdauer von Anfang eines Minimum bis zum Ende des darauffolgenden Maximums while Zyklus < Zyklenanzahl + 1: print('Aktueller Strompreiszyklus in dem Optimiert wird:', Zyklus) SOC = get_SOC(array_names, liste_ladephasen, Zyklus) entladedauer = get_entladedauer(array_names, SOC, Zyklus) ladedauer = reverse_ladedauer(array_names, SOC, Zyklus) print('SOC', SOC) print('entladedauer', entladedauer) print('ladedauer', ladedauer) liste_ladephasen[Zyklus - 1, 0] = liste_minima[Zyklus - 1] - (ladedauer / (2 * 3600)) liste_ladephasen[Zyklus - 1, 1] = liste_minima[Zyklus - 1] + (ladedauer / (2 * 3600)) print('liste_ladephasen', liste_ladephasen) liste_entladephasen[Zyklus - 1, 0] = liste_maxima[Zyklus - 1] - (entladedauer / (3 * 3600)) # &&& liste_entladephasen[Zyklus - 1, 1] = liste_maxima[Zyklus - 1] + (2 * entladedauer / (3 * 3600)) # &&& print('liste_entladephasen', liste_entladephasen) correct_left_result = correct_left(liste_ladephasen, liste_entladephasen, Zyklus, liste_minima) liste_ladephasen[Zyklus - 1, :] = correct_left_result[0][Zyklus - 1, :] liste_entladephasen[Zyklus - 1, :] = correct_left_result[1][Zyklus - 1, :] print('liste_phasen nach correct left', liste_ladephasen, liste_entladephasen) correct_right_result = correct_right(liste_ladephasen, liste_entladephasen, Zyklus, liste_maxima, liste_minima, array_names) liste_ladephasen[Zyklus - 1, :] = correct_right_result[0][Zyklus - 1, :] liste_entladephasen[Zyklus - 1, :] = correct_right_result[1][Zyklus - 1, :] print('liste_phasen nach correct right', liste_ladephasen, liste_entladephasen) ergebnis = np.array([[0, 0]]) ladedauer_neu = liste_ladephasen[Zyklus - 1, 1] - liste_ladephasen[Zyklus - 1, 0] print('ladedauer_neu_check', ladedauer_neu) better = True opt = 1 #Nummer des Optimierungsdurchgangs in dem jeweiligen Strompreiszyklus while better == True: #solange sich die Stromkosten verkleinern werden die Phasen verkürzt if liste_ladephasen[Zyklus - 1, 0] == 0 and liste_ladephasen[Zyklus - 1, 1] == 0: break ladephase_neu = np.array([[ liste_minima[Zyklus - 1] - (ladedauer_neu / (2)), liste_minima[Zyklus - 1] + (ladedauer_neu / (2)) ]]) SOC_neu = get_SOC(array_names, ladephase_neu, Zyklus) entladedauer_neu = get_entladedauer(array_names, SOC_neu, Zyklus) print('SOC:', SOC_neu) print('entladedauer:', entladedauer_neu) entladephase_neu = np.array([[ liste_maxima[Zyklus - 1] - (entladedauer_neu / (3 * 3600)), liste_maxima[Zyklus - 1] + (2 * entladedauer_neu / (3 * 3600)) ]]) # &&& print('ladephase die getestet wird:', ladephase_neu) print('entladephase die getestet wird:', entladephase_neu) input_laden = merge(ladephase_neu, dir_laden_daten) input_entladen = merge(entladephase_neu, dir_laden_daten) try: #erzeuge Instanz von Dymola dymola = DymolaInterface() dymola.openModel(path=dir_modell_sim) dymola.translateModel(problem=name_modell_sim) dymola.ExecuteCommand("laden.table=" + input_laden) dymola.ExecuteCommand("entladen.table=" + input_entladen) result = dymola.simulateExtendedModel( problem=name_modell_sim, stopTime=simulationsdauer * 3600, method='radau IIa', finalNames=['Stromkosten.y'], resultFile=os.path.join(Root_simulationsergebnisse, 'optimization_test')) Stromkosten = result[1] column = np.array([ladedauer_neu, Stromkosten[0]]) ergebnis = np.vstack((ergebnis, column)) print('aktuelle Stromkosten', Stromkosten[0]) if not result: print("Simulation failed. Below is the translation log.") log = dymola.getLastError() print(log) dymola.plot(["elektrische_leistungsaufnahme.y"]) dymola.ExportPlotAsImage( os.path.join( Root_simulationsergebnisse, "Ergebnis_von" + str(Zyklus) + str(opt) + ".png")) except DymolaException as ex: print("Error: " + str(ex)) if dymola is not None: dymola.close() dymola = None print( 'Optimierungsdurchgang der in dem Entsprechenden Strompreiszyklus durchgeführt wurde', opt) if opt > 1: if ergebnis[opt, 1] < ergebnis[opt - 1, 1]: better = True else: better = False else: better = True print('better:', better) if better == True: liste_ladephasen[Zyklus - 1, :] = ladephase_neu liste_entladephasen[Zyklus - 1, :] = entladephase_neu ladedauer_neu = ladedauer_neu * 0.9 #ladedauer wird um 10% verkürzt opt = opt + 1 if ergebnis[opt - 2, 1] > ergebnis_compare: print('hier_ergebnis', ergebnis) print('hier_ladeph', liste_ladephasen) print('hier_opt', opt) liste_ladephasen[Zyklus - 1, :] = np.zeros((1, 2)) liste_entladephasen[Zyklus - 1, :] = np.zeros((1, 2)) print('hier_ladeph', liste_ladephasen) Zyklus = Zyklus + 1 print('ergebnis_tabelle des Zyklusses', ergebnis) #&&& hier einfügen, dass eine Lade/und Entladephase nur verwendet wird, wenn das ergebnis besser als das vergleichsergebnis ist return liste_ladephasen, liste_entladephasen
def simulate(simSettings, showWindow=False, closeWindow=True, simID='', seed=0, singleTranslate=True): ''' simSettings => dictionary of setting parameters (see below for details) showWindow => =True to launch Dymola GUI closeWindow => =False to prevent auto-closing of the Dymola GUI when done simID => simulation ID to differentiate output files (e.g., simID_dsres0.mat vs. dsres0.mat) seed => starting seed value for output file naming (e.g., seed+0, ..., seed+len(experiments)) singleTranslate => =True to only translate the model once - !!! If variables needed to be changed require retranslation then add them to problem name. i.e., simSettings['problem']=['Example.Test(var1=1,var2=5)'] or try to set 'annotation(Evaluate=false)' in the model simSettings details: - All settings, besides `=None`, must be enclosed in brackets [] - !!! 'initialNames' and 'initialValues' are set different than others. Specify each variable indepenently. The script will generate the tests and collapse all 'non-standard' keys. - 'problem', 'resultFile', and 'autoLoad' only support 1 or None entries - Only specify 'numberOfIntervals' or 'outputInterval', not both - 'fixedstepsize' is only for fixed step size solvers - showWindow=True and closeWindow=False only a specified number of simulations are retained in memory according, not all simulations. - The experiments generated are a list of dictionaries which are saved as experiments.pickle in the working directory of the Modelica simulation (cwdMOD). To open the pickle in python: with open(os.path.join('PATHTOPICKLE,'experiments.pickle'), 'rb') as handle: experiments = pickle.load(handle) - !!! Settings not specified assume Dymola default settings. Any simulation settings (tolerance, solver, etc.) located in the model are ignored. Default Settings: 'problem' = '' => Modelica file (.mo) to be run (e.g., ['TRANSFORM.Fluid.Examples.RankineCycl'] ) 'startTime' = 0 => Start time of simulation 'stopTime' = 1 => Stop time of simulation 'numberOfIntervals' = 500 => Number of intervals to be saved to result file 'outputInterval' = 0 => Time (seconds) between intervals to be saved to result file 'method' = 'dassl' => Solver 'tolerance' = 0.0001 => Solver tolerance 'fixedstepsize' = 0 => Step size for solver (certain solvers only, e.g., Euler) 'resultFile' = 'dsres.mat' => Name of the result file 'initialNames' = '' => Names of variables in model 'initialValues' = '' => Value of variables in model (len(initialNames) = len(initialValues)) 'finalNames' = '' => Variable for Dymola to print to screen when simulation is finished 'autoLoad' = true => Automatically load (true) the result file into the Dymola plot window Possible Methods: 'methods' = Lsodar, dassl, Euler, Rkfix2, Rkfix3, Rkfix4, Esdirk23a, Esdirk34a, Esdirk45a, Dopri45, Dopri853, Sdirk34hw, Cerk23, Cerk34, Cerk34, Cvode For the current supported solvers and their use see Dymola ''' # Check User Input checkInput(simSettings) try: if int(seed) >= 0: seed = int(seed) else: raise NameError("seedNum must be a positive integer") except: raise NameError("seedNum must be a positive integer") # Modify simID for naminc conventions if simID != '': simID = simID + '_' # Generate all experiment permutations experimentsRaw = genExperimentsRaw(simSettings) # Filter experiments to generate key/value pairs for 'initialNames' and 'initialValues' experiments = genExperiments(experimentsRaw) # Instantiate the Dymola interface and start Dymola dymola = None result_tran = False try: # Open Dymola dymola = DymolaInterface(showwindow=showWindow) # Get working directory cwdMod = dymola.ExecuteCommand( 'Modelica.Utilities.System.getWorkDirectory();') # Translate the model if singleTranslate: result_tran = dymola.translateModel(experiments[0]['problem']) if not result_tran: raise Exception( "Translation failed. Aborting parametric simulation. Investigate model in IDE for details." ) # Run all experiments saveResult = [] j = seed print('Total experiments = {} for simID = "{}"'.format( len(experiments), simID)) print('Experiment numbering started at seed = {}'.format(seed)) for i, value in enumerate(experiments): j = seed + i print('Experiment {} (= {}/{})'.format(j, i + 1, len(experiments))) print(value) # ModelTranslate = "Dymola.Path.To.Your.Model(Dymola.Path.to.Variable=1000)" if not singleTranslate: result_tran = False result_tran = dymola.translateModel(value['problem']) if not result_tran: print( "Translation failed. Aborting parametric simulation. Investigate model in IDE for details." ) break # Simulate the model result = dymola.simulateExtendedModel(**value)[0] # Save the result (success/fail) saveResult.append(result) # Rename the log files and return new log file for debugging ref. dslogNew = renameFiles(simID, j, value, cwdMod, result) # Print last line of error if not result: print( "Simulation failed. Below is the translation log. For more details see: {}" .format(dslogNew)) log = dymola.getLastErrorLog() print('### Log Start ###\n' + log + '### Log End ###') except DymolaException as ex: print(("Error: " + str(ex))) except Exception as inst: print('{}'.format(inst.message)) finally: if dymola is not None: if showWindow == True and closeWindow == False: pass else: dymola.close() if result_tran: # Save experiment dictionary as pickle in cwdMod with open( os.path.join( cwdMod, '{}experiments_{}to{}.pickle'.format(simID, seed, j)), 'wb') as handle: pickle.dump(experiments, handle, protocol=pickle.HIGHEST_PROTOCOL) # Save summary off success/fail (true/false) of simulations with open( os.path.join(cwdMod, '{}summary_{}to{}.txt'.format(simID, seed, j)), 'w') as fil: fil.write('Summary of success/fail (true/false) of experiments\n') for i, val in enumerate(saveResult): fil.write('\t'.join( ['Experiment', '{}'.format(i), '{}'.format(val)]) + '\n')