def run_demo(with_plots=True): """This example demonstrates how the Python interface to the three different ASTs in the compiler can be used. The JPype package is used to create Java objects in a Java Virtual Machine which is seamlessly integrated with the Python shell. The Java objects can be accessed interactively and methods of the object can be invoked. For more information about the Java classes and their methods used in this example, please consult the API documentation for the Modelica compiler, <a href=http://www.jmodelica.org/page/22>. Notice however that the documentation for the compiler front-ends is still very rudimentary. Also, the interfaces to the source and instance AST will be made more user friendly in upcoming versions. Three different usages of ASTs are shown: 1. Count the number of classes in the Modelica standard library. In this example, a Python function is defined to traverse the source AST which results from parsing of the Modelica standard library. 2. Instantiate the CauerLowPassAnalog model. The instance AST for this model is dumped and it is demonstrated how the merged modification environments can be accessed. 3. Flatten the CauerLowPassAnalog model instance and print some statistics of the flattened Model. """ curr_dir = os.path.dirname(os.path.abspath(__file__)) # Create a compiler mc = ModelicaCompiler() # Don't parse the file if it har already been parsed. try: source_root.getProgramRoot() except: # Parse the file CauerLowPassAnalog.mo and get the root node # of the source AST source_root = mc.parse_model(curr_dir + "/files/CauerLowPassAnalog.mo") # Don't load the standard library if it is already loaded try: modelica.getName().getID() except NameError, e: # Load the Modelica standard library and get the class # declaration AST node corresponding to the Modelica # package. modelica = source_root.getProgram().getLibNode(1). \ getStoredDefinition().getElement(0)
def run_demo(with_plots=True): """ An example on how to simulate a model using the DAE simulator. The result can be compared with that of sim_rlc.py which has solved the same problem using dymola. Also writes information to a file. """ curr_dir = os.path.dirname(os.path.abspath(__file__)); model_name = 'RLC_Circuit' mofile = curr_dir+'/files/RLC_Circuit.mo' mc = ModelicaCompiler() # Comile the Modelica model first to C code and # then to a dynamic library mc.compile_model(mofile,model_name,target='ipopt') # Load the dynamic library and XML data model=jmi.Model(model_name) # Create DAE initialization object. init_nlp = NLPInitialization(model) # Create an Ipopt solver object for the DAE initialization system init_nlp_ipopt = InitializationOptimizer(init_nlp) # Solve the DAE initialization system with Ipopt init_nlp_ipopt.init_opt_ipopt_solve() simulator = SundialsDAESimulator(model, verbosity=3, start_time=0.0, final_time=30.0, time_step=0.01) simulator.run() simulator.write_data() # Load the file we just wrote to file res = jmodelica.io.ResultDymolaTextual('RLC_Circuit_result.txt') sine_y = res.get_variable_data('sine.y') resistor_v = res.get_variable_data('resistor.v') inductor1_i = res.get_variable_data('inductor1.i') assert N.abs(resistor_v.x[-1] - 0.159255008028) < 1e-3, \ "Wrong value in simulation result in RLC.py" #Ts, ys = simulator.get_solution('sine.y','resistor.v','inductor1.i') fig = p.figure() p.plot(sine_y.t, sine_y.x, resistor_v.t, resistor_v.x, inductor1_i.t, inductor1_i.x) p.legend(('sine.y','resistor.v','inductor1.i')) p.show()
def run_demo(with_plots=True): mc = ModelicaCompiler() # Comile the Modelica model first to C code and # then to a dynamic library mofile = 'RLC_Circuit.mo' optpackage = 'RLC_Circuit' path = get_example_path() os.chdir(path) mc.compile_model(os.path.join(path, mofile), optpackage, target='ipopt') # Load the dynamic library and XML data rlc=jmi.Model('RLC_Circuit') # Create DAE initialization object. init_rlc = NLPInitialization(rlc) # Create an Ipopt solver object for the DAE initialization system init_rlc_ipopt = InitializationOptimizer(init_rlc) # Solve the DAE initialization system with Ipopt init_rlc_ipopt.init_opt_ipopt_solve() # Simulate system... # Verify solution by loading result file generated by dymola res = jmodelica.io.ResultDymolaBinary('RLC_Circuit_dymola.mat') # Get result variables V_in = res.get_variable_data('sine.y') V_resistor = res.get_variable_data('resistor.v') I_inductor1 = res.get_variable_data('inductor1.i') if with_plots: plt.figure(1) plt.clf() plt.hold(True) plt.plot(V_in.t,V_in.x) plt.plot(V_resistor.t,V_resistor.x) plt.plot(I_inductor1.t,I_inductor1.x) plt.show()
def test_state_start_values_fixed(self): """ Test of the compiler option state_start_values_fixed """ """ Test of the dae_get_sizes in Model """ model = os.path.join("files", "VDP_pack.mo") fpath = os.path.join(path_to_tests, model) cpath = "VDP_pack.VDP" fname = cpath.replace('.', '_', 1) mc = ModelicaCompiler() mc.set_boolean_option('state_start_values_fixed', False) mc.compile_model(fpath, cpath) # Load the dynamic library and XML data vdp = jmi.Model(fname) res_n_eq_F = 2 n_eq_F, n_eq_R = vdp.jmimodel.dae_get_sizes() assert n_eq_F==res_n_eq_F, \ "test_jmi.py: test_Model_dae_get_sizes: Wrong number of DAE equations." res_n_eq_F0 = 2 res_n_eq_F1 = 5 res_n_eq_Fp = 0 res_n_eq_R0 = 0 n_eq_F0, n_eq_F1, n_eq_Fp, n_eq_R0 = vdp.jmimodel.init_get_sizes() assert n_eq_F0==res_n_eq_F0 and n_eq_F1==res_n_eq_F1 and n_eq_Fp==res_n_eq_Fp and n_eq_R0==res_n_eq_R0, \ "test_jmi.py: test_Model_dae_get_sizes: Wrong number of DAE initialization equations."
def run_demo(with_plots=True): """ Load change of a distillation column. The distillation column model is documented in the paper: @Article{hahn+02, title={An improved method for nonlinear model reduction using balancing of empirical gramians}, author={Hahn, J. and Edgar, T.F.}, journal={Computers and Chemical Engineering}, volume={26}, number={10}, pages={1379-1397}, year={2002} } """ curr_dir = os.path.dirname(os.path.abspath(__file__)) # Create a Modelica compiler instance mc = ModelicaCompiler() # Compile the stationary initialization model into a DLL mc.compile_model(curr_dir + "/files/DISTLib.mo", "DISTLib.Binary_Dist_initial", target='ipopt') # Load a model instance into Python init_model = jmi.Model("DISTLib_Binary_Dist_initial") # Create DAE initialization object. init_nlp = NLPInitialization(init_model) # Create an Ipopt solver object for the DAE initialization system init_nlp_ipopt = InitializationOptimizer(init_nlp) # Set inputs for Stationary point A u1_0_A = 3.0 init_model.set_value('u1', u1_0_A) # init_nlp_ipopt.init_opt_ipopt_set_string_option("derivative_test","first-order") #init_nlp_ipopt.init_opt_ipopt_set_int_option("max_iter",5) # Solve the DAE initialization system with Ipopt init_nlp_ipopt.init_opt_ipopt_solve() # Store stationary point A y_A = N.zeros(32) x_A = N.zeros(32) # print(' *** Stationary point A ***') print '(Tray index, x_i_A, y_i_A)' for i in range(N.size(y_A)): y_A[i] = init_model.get_value('y' + str(i + 1)) x_A[i] = init_model.get_value('x' + str(i + 1)) print '(' + str(i + 1) + ', %f, %f)' % (x_A[i], y_A[i]) # Set inputs for stationary point B u1_0_B = 3.0 - 1 init_model.set_value('u1', u1_0_B) # init_nlp_ipopt.init_opt_ipopt_set_string_option("derivative_test","first-order") #init_nlp_ipopt.init_opt_ipopt_set_int_option("max_iter",5) # Solve the DAE initialization system with Ipopt init_nlp_ipopt.init_opt_ipopt_solve() # Store stationary point B y_B = N.zeros(32) x_B = N.zeros(32) # print(' *** Stationary point B ***') print '(Tray index, x_i_B, y_i_B)' for i in range(N.size(y_B)): y_B[i] = init_model.get_value('y' + str(i + 1)) x_B[i] = init_model.get_value('x' + str(i + 1)) print '(' + str(i + 1) + ', %f, %f)' % (x_B[i], y_B[i]) # ## Set up and solve an optimal control problem. # Create an OptimicaCompiler instance oc = OptimicaCompiler() # Generate initial equations for states even if fixed=false oc.set_boolean_option('state_start_values_fixed', True) # Compil the Model oc.compile_model( (curr_dir + "/files/DISTLib.mo", curr_dir + "/files/DISTLib_Opt.mo"), "DISTLib_Opt.Binary_Dist_Opt1", target='ipopt') # Load the dynamic library and XML data model = jmi.Model("DISTLib_Opt_Binary_Dist_Opt1") # Initialize the model with parameters # Initialize the model to stationary point A for i in range(N.size(x_A)): model.set_value('x' + str(i + 1) + '_0', x_A[i]) # Set the target values to stationary point B model.set_value('u1_ref', u1_0_B) model.set_value('y1_ref', y_B[0]) # Initialize the optimization mesh n_e = 50 # Number of elements hs = N.ones(n_e) * 1. / n_e # Equidistant points n_cp = 3 # Number of collocation points in each element # Create an NLP object representing the discretized problem nlp = ipopt.NLPCollocationLagrangePolynomials(model, n_e, hs, n_cp) # Create an Ipopt NLP object nlp_ipopt = ipopt.CollocationOptimizer(nlp) #nlp_ipopt.opt_sim_ipopt_set_string_option("derivative_test","first-order") # If the convergence is slow, may increase tolerance. #nlp_ipopt.opt_sim_ipopt_set_num_option("tol",0.0001) #Solve the optimization problem nlp_ipopt.opt_sim_ipopt_solve() # Write to file. The resulting file can be # loaded into Dymola. nlp.export_result_dymola() # Load the file we just wrote res = jmodelica.io.ResultDymolaTextual( 'DISTLib_Opt_Binary_Dist_Opt1_result.txt') # Extract variable profiles u1_res = res.get_variable_data('u1') u1_ref_res = res.get_variable_data('u1_ref') y1_ref_res = res.get_variable_data('y1_ref') x_res = [] x_ref_res = [] for i in range(N.size(x_B)): x_res.append(res.get_variable_data('x' + str(i + 1))) y_res = [] for i in range(N.size(x_B)): y_res.append(res.get_variable_data('y' + str(i + 1))) # Plot the results if with_plots: plt.figure(1) plt.clf() plt.hold(True) plt.subplot(311) plt.title('Liquid composition') plt.plot(x_res[0].t, x_res[0].x) plt.ylabel('x1') plt.grid() plt.subplot(312) plt.plot(x_res[16].t, x_res[16].x) plt.ylabel('x17') plt.grid() plt.subplot(313) plt.plot(x_res[31].t, x_res[31].x) plt.ylabel('x32') plt.grid() plt.xlabel('t [s]') plt.show() # Plot the results plt.figure(2) plt.clf() plt.hold(True) plt.subplot(311) plt.title('Vapor composition') plt.plot(y_res[0].t, y_res[0].x) plt.plot(y1_ref_res.t, y1_ref_res.x, '--') plt.ylabel('y1') plt.grid() plt.subplot(312) plt.plot(y_res[16].t, y_res[16].x) plt.ylabel('y17') plt.grid() plt.subplot(313) plt.plot(y_res[31].t, y_res[31].x) plt.ylabel('y32') plt.grid() plt.xlabel('t [s]') plt.show() plt.figure(3) plt.clf() plt.hold(True) plt.plot(u1_res.t, u1_res.x) plt.ylabel('u') plt.plot(u1_ref_res.t, u1_ref_res.x, '--') plt.xlabel('t [s]') plt.title('Reflux ratio') plt.grid() plt.show()
from jmodelica.compiler import ModelicaCompiler from jmodelica.compiler import OptimicaCompiler import jmodelica as jm jm_home = jm.environ['JMODELICA_HOME'] path_to_examples = os.path.join('Python', 'jmodelica', 'examples') model_mc = os.path.join('files', 'Pendulum_pack_no_opt.mo') fpath_mc = os.path.join(jm_home, path_to_examples, model_mc) cpath_mc = "Pendulum_pack.Pendulum" model_oc = os.path.join('files', 'Pendulum_pack.mo') fpath_oc = os.path.join(jm_home, path_to_examples, model_oc) cpath_oc = "Pendulum_pack.Pendulum_Opt" mc = ModelicaCompiler() ModelicaCompiler.set_log_level(ModelicaCompiler.LOG_ERROR) mc.set_boolean_option('state_start_values_fixed', True) oc = OptimicaCompiler() OptimicaCompiler.set_log_level(OptimicaCompiler.LOG_ERROR) oc.set_boolean_option('state_start_values_fixed', True) @testattr(stddist=True) def test_compile(): """ Test that compilation is possible with compiler and that all obligatory files are created. """
import nose from jmodelica.simulation.sundials import SundialsODESimulator from jmodelica.simulation.sundials import SundialsDAESimulator from jmodelica.tests import testattr import jmodelica.simulation.sundials as sundials import jmodelica.simulation import jmodelica.jmi as jmi from jmodelica.compiler import ModelicaCompiler from jmodelica.compiler import OptimicaCompiler jm_home = os.environ.get('JMODELICA_HOME') path_to_examples = os.path.join(jm_home, "Python", "jmodelica", "examples") path_to_tests = os.path.join(jm_home, "Python", "jmodelica", "tests") mc = ModelicaCompiler() oc = OptimicaCompiler() oc.set_boolean_option('state_start_values_fixed', True) sep = os.path.sep class TestSundialsDAESimulator: @classmethod def setUpClass(cls): """Compile the test model. (This is only run once during the test)""" modelf = "files" + sep + "Pendulum_pack_no_opt.mo" fpath = os.path.join(path_to_examples, modelf) cpath = "Pendulum_pack.Pendulum" fname = cpath.replace('.', '_', 1) mc.compile_model(fpath, cpath)
# # 2. An optimal control problem is solved where the objective # Is to transfer the state of the system from stationary # point A to point B. Here, it is also demonstrated how # to set parameter values in a model. More information # about the simultaneous optimization algorithm can be # found at http://www.jmodelica.org/page/10. # # 3. The optimization result is saved to file and then # the important variables are plotted. # curr_dir = os.path.dirname(os.path.abspath(__file__)) # Create a Modelica compiler instance mc = ModelicaCompiler() # Don't generate initial equations for states if fixed=false mc.set_boolean_option('state_start_values_fixed', False) # Compile the stationary initialization model into a DLL mc.compile_model(curr_dir + "/files/CSTRLib.mo", "CSTRLib.Components.Two_CSTRs_stat_init", target='ipopt') #mc.compile_dll("CSTRLib_Components_Two_CSTRs_stat_init",target='ipopt') # Load a model instance into Python init_model = jmi.Model("CSTRLib_Components_Two_CSTRs_stat_init") # Create DAE initialization object. init_nlp = jmi.DAEInitializationOpt(init_model)
def run_demo(with_plots=True): """This example is based on a system composed of two Continously Stirred Tank Reactors (CSTRs) in series. The example demonstrates the following steps: 1. How to solve a DAE initialization problem. The initialization model have equations specifying that all derivatives should be identically zero, which implies that a stationary solution is obtained. Two stationary points, corresponding to different inputs, are computed. We call the stationary points A and B respectively. For more information about the DAE initialization algorithm, see http://www.jmodelica.org/page/10. 2. An optimal control problem is solved where the objective Is to transfer the state of the system from stationary point A to point B. Here, it is also demonstrated how to set parameter values in a model. More information about the simultaneous optimization algorithm can be found at http://www.jmodelica.org/page/10. 3. The optimization result is saved to file and then the important variables are plotted.""" curr_dir = os.path.dirname(os.path.abspath(__file__)) # Create a Modelica compiler instance mc = ModelicaCompiler() # Compile the stationary initialization model into a DLL mc.compile_model(curr_dir + "/files/CSTRLib.mo", "CSTRLib.Components.Two_CSTRs_stat_init", target='ipopt') # Load a model instance into Python init_model = jmi.Model("CSTRLib_Components_Two_CSTRs_stat_init") # Create DAE initialization object. init_nlp = NLPInitialization(init_model) # Create an Ipopt solver object for the DAE initialization system init_nlp_ipopt = InitializationOptimizer(init_nlp) # Set inputs for Stationary point A u1_0_A = 1 u2_0_A = 1 init_model.set_value('u1', u1_0_A) init_model.set_value('u2', u2_0_A) # init_nlp_ipopt.init_opt_ipopt_set_string_option("derivative_test","first-order") #init_nlp_ipopt.init_opt_ipopt_set_int_option("max_iter",5) # Solve the DAE initialization system with Ipopt init_nlp_ipopt.init_opt_ipopt_solve() # Store stationary point A CA1_0_A = init_model.get_value('CA1') CA2_0_A = init_model.get_value('CA2') T1_0_A = init_model.get_value('T1') T2_0_A = init_model.get_value('T2') # Print some data for stationary point A print(' *** Stationary point A ***') print('u = [%f,%f]' % (u1_0_A, u2_0_A)) print('CAi = [%f,%f]' % (CA1_0_A, CA2_0_A)) print('Ti = [%f,%f]' % (T1_0_A, T2_0_A)) # Set inputs for stationary point B u1_0_B = 1.1 u2_0_B = 0.9 init_model.set_value('u1', u1_0_B) init_model.set_value('u2', u2_0_B) # init_nlp_ipopt.init_opt_ipopt_set_string_option("derivative_test","first-order") #init_nlp_ipopt.init_opt_ipopt_set_int_option("max_iter",5) # Solve the DAE initialization system with Ipopt init_nlp_ipopt.init_opt_ipopt_solve() # Stationary point B CA1_0_B = init_model.get_value('CA1') CA2_0_B = init_model.get_value('CA2') T1_0_B = init_model.get_value('T1') T2_0_B = init_model.get_value('T2') # Print some data for stationary point B print(' *** Stationary point B ***') print('u = [%f,%f]' % (u1_0_B, u2_0_B)) print('CAi = [%f,%f]' % (CA1_0_B, CA2_0_B)) print('Ti = [%f,%f]' % (T1_0_B, T2_0_B)) ## Set up and solve an optimal control problem. # Create an OptimicaCompiler instance oc = OptimicaCompiler() # Compil the Model oc.compile_model( (curr_dir + "/files/CSTRLib.mo", curr_dir + "/files/CSTR2_Opt.mo"), "CSTR2_Opt", target='ipopt') # Load the dynamic library and XML data model = jmi.Model("CSTR2_Opt") # Initialize the model with parameters # Initialize the model to stationary point A model.set_value('two_CSTRs_Series.CA1_0', CA1_0_A) model.set_value('two_CSTRs_Series.CA2_0', CA2_0_A) model.set_value('two_CSTRs_Series.T1_0', T1_0_A) model.set_value('two_CSTRs_Series.T2_0', T2_0_A) # Set the target values to stationary point B model.set_value('u1_ref', u1_0_B) model.set_value('u2_ref', u2_0_B) model.set_value('CA1_ref', CA1_0_B) model.set_value('CA2_ref', CA2_0_B) # Initialize the optimization mesh n_e = 30 # Number of elements hs = N.ones(n_e) * 1. / n_e # Equidistant points n_cp = 3 # Number of collocation points in each element # Create an NLP object representing the discretized problem nlp = ipopt.NLPCollocationLagrangePolynomials(model, n_e, hs, n_cp) # Create an Ipopt NLP object nlp_ipopt = ipopt.CollocationOptimizer(nlp) #nlp_ipopt.opt_sim_ipopt_set_string_option("derivative_test","first-order") # The convergence is slow, for some reason, increasing tolerance. nlp_ipopt.opt_sim_ipopt_set_num_option("tol", 0.0001) #Solve the optimization problem nlp_ipopt.opt_sim_ipopt_solve() # Write to file. The resulting file (CSTR2_Opt_result.txt) can be # loaded into Dymola. nlp.export_result_dymola() # Load the file we just wrote res = jmodelica.io.ResultDymolaTextual('CSTR2_Opt_result.txt') # Extract variable profiles CA1_res = res.get_variable_data('two_CSTRs_Series.CA1') CA2_res = res.get_variable_data('two_CSTRs_Series.CA2') T1_res = res.get_variable_data('two_CSTRs_Series.T1') T2_res = res.get_variable_data('two_CSTRs_Series.T2') u1_res = res.get_variable_data('two_CSTRs_Series.u1') u2_res = res.get_variable_data('two_CSTRs_Series.u2') CA1_ref_res = res.get_variable_data('CA1_ref') CA2_ref_res = res.get_variable_data('CA2_ref') u1_ref_res = res.get_variable_data('u1_ref') u2_ref_res = res.get_variable_data('u2_ref') # Plot the results if with_plots: plt.figure(1) plt.clf() plt.hold(True) plt.subplot(211) plt.plot(CA1_res.t, CA1_res.x) plt.plot(CA1_ref_res.t, CA1_ref_res.x, '--') plt.ylabel('Concentration reactor 1 [J/l]') plt.grid() plt.subplot(212) plt.plot(CA2_res.t, CA2_res.x) plt.plot(CA2_ref_res.t, CA2_ref_res.x, '--') plt.ylabel('Concentration reactor 2 [J/l]') plt.xlabel('t [s]') plt.grid() plt.show() plt.figure(2) plt.clf() plt.hold(True) plt.subplot(211) plt.plot(T1_res.t, T1_res.x) plt.ylabel('Temperature reactor 1 [K]') plt.grid() plt.subplot(212) plt.plot(T2_res.t, T2_res.x) plt.ylabel('Temperature reactor 2 [K]') plt.grid() plt.xlabel('t [s]') plt.show() plt.figure(3) plt.clf() plt.hold(True) plt.subplot(211) plt.plot(u1_res.t, u1_res.x) plt.ylabel('Input 1') plt.plot(u1_ref_res.t, u1_ref_res.x, '--') plt.grid() plt.subplot(212) plt.plot(u2_res.t, u2_res.x) plt.ylabel('Input 2') plt.plot(u2_ref_res.t, u2_ref_res.x, '--') plt.xlabel('t [s]') plt.grid() plt.show()