def test_rp_example3(): m = rp_example3() with pytest.raises(RuntimeError): petsc.petsc_dae_by_time_element( m, time=m.time, )
def test_petsc_read_trajectory(): """ Check that the PETSc DAE solver works. """ m, y1, y2, y3, y4, y5, y6 = dae_with_non_time_indexed_constraint() m.scaling_factor = pyo.Suffix(direction=pyo.Suffix.EXPORT) m.scaling_factor[m.y[180, 1]] = 10 # make sure unscale works petsc.petsc_dae_by_time_element( m, time=m.t, ts_options={ "--ts_type": "cn", # Crank–Nicolson "--ts_adapt_type": "basic", "--ts_dt": 0.01, "--ts_save_trajectory": 1, "--ts_trajectory_type": "visualization", }, vars_stub="tj_random_junk_123", trajectory_save_prefix="tj_random_junk_123", ) assert pytest.approx(y1, rel=1e-3) == pyo.value(m.y[m.t.last(), 1]) assert pytest.approx(y2, rel=1e-3) == pyo.value(m.y[m.t.last(), 2]) assert pytest.approx(y3, rel=1e-3) == pyo.value(m.y[m.t.last(), 3]) assert pytest.approx(y4, rel=1e-3) == pyo.value(m.y[m.t.last(), 4]) assert pytest.approx(y5, rel=1e-3) == pyo.value(m.y[m.t.last(), 5]) assert pytest.approx(y6, rel=1e-3) == pyo.value(m.y[m.t.last(), 6]) tj = petsc.PetscTrajectory(json="tj_random_junk_123_1.json.gz") assert tj.get_dt()[0] == pytest.approx( 0.01) # if small enough shouldn't be cut assert tj.get_vec(m.y[180, 1])[-1] == pytest.approx(y1, rel=1e-3) assert tj.get_vec("_time")[-1] == pytest.approx(180) times = np.linspace(0, 180, 181) vecs = tj.interpolate_vecs(times) assert vecs[str(m.y[180, 1])][180] == pytest.approx(y1, rel=1e-3) assert vecs["_time"][180] == pytest.approx(180) tj.to_json("some_testy_json.json") with open("some_testy_json.json", "r") as fp: vecs = json.load(fp) assert vecs[str(m.y[180, 1])][-1] == pytest.approx(y1, rel=1e-3) assert vecs["_time"][-1] == pytest.approx(180) os.remove("some_testy_json.json") tj.to_json("some_testy_json.json.gz") tj2 = petsc.PetscTrajectory(json="some_testy_json.json.gz") assert tj2.vecs[str(m.y[180, 1])][-1] == pytest.approx(y1, rel=1e-3) assert tj2.vecs["_time"][-1] == pytest.approx(180) os.remove("some_testy_json.json.gz") tj2 = petsc.PetscTrajectory(vecs=vecs) assert tj2.vecs[str(m.y[180, 1])][-1] == pytest.approx(y1, rel=1e-3) assert tj2.vecs["_time"][-1] == pytest.approx(180)
def test_rp_example4(): m = rp_example4() petsc.petsc_dae_by_time_element(m, time=m.time, ts_options={ "--ts_dt": 1, "--ts_adapt_type": "none", }) assert pyo.value(m.u[10]) == pytest.approx(398) assert pyo.value(m.x[10]) == pytest.approx(20)
def test_car(): m = car_example() m.a.fix(1.0) m.tf.fix(16.56) # solve petsc.petsc_dae_by_time_element( m, time=m.tau, ts_options={ "--ts_type": "cn", # Crank–Nicolson "--ts_adapt_type": "basic", "--ts_dt": 0.01, }, ) assert pyo.value(m.x[1]) == pytest.approx(131.273, rel=1e-2)
def test_petsc_dae_idaes_solve(): """ Check that the PETSc DAE solver works. """ m, y1, y2, y3, y4, y5, y6 = dae() petsc.petsc_dae_by_time_element( m, time=m.t, ts_options={ "--ts_type": "cn", # Crank–Nicolson "--ts_adapt_type": "basic", "--ts_dt": 0.1, }, ) assert pytest.approx(y1, rel=1e-3) == pyo.value(m.y[m.t.last(), 1]) assert pytest.approx(y2, rel=1e-3) == pyo.value(m.y[m.t.last(), 2]) assert pytest.approx(y3, rel=1e-3) == pyo.value(m.y[m.t.last(), 3]) assert pytest.approx(y4, rel=1e-3) == pyo.value(m.y[m.t.last(), 4]) assert pytest.approx(y5, rel=1e-3) == pyo.value(m.y[m.t.last(), 5]) assert pytest.approx(y6, rel=1e-3) == pyo.value(m.y6[m.t.last()])
def test_petsc_with_pid_model(): m = create_model( time_set=[0, 24], nfe=1, calc_integ=True, ) # time_var will be an explicit time variable we can use in constraints. m.fs.time_var = pyo.Var(m.fs.time) # We'll add a constraint to calculate the inlet pressure based on time, # so we need to unfix pressure. m.fs.valve_1.control_volume.properties_in[0].pressure.unfix() m.fs.valve_1.control_volume.properties_in[24].pressure.unfix() # The solver will directly set the time variable for the DAE solve, but # solving the initial conditions is just a system of nonlinear equations, # so we need to fix the initial time. m.fs.time_var[0].fix(m.fs.time.first()) # We could break up the time domain and solve this in pieces, but creative use # of min and max will let us create the ramping function we want. # From 10s to 12s ramp inlet pressure from 500,000 Pa to 600,000 Pa @m.fs.Constraint(m.fs.time) def inlet_pressure_eqn(b, t): return b.valve_1.control_volume.properties_in[t].pressure == \ smooth_min(600000, smooth_max(500000, 50000*(b.time_var[t] - 10) + 500000)) res = petsc.petsc_dae_by_time_element( m, time=m.fs.time, timevar=m.fs.time_var, ts_options={ "--ts_type": "beuler", "--ts_dt": 0.1, "--ts_monitor": "", # set initial step to 0.1 "--ts_save_trajectory": 1, "--ts_trajectory_type": "visualization", }, vars_stub="tj_vars") # read the trajectory data, and make it easy by interpolating a time point # every second tj = petsc.PetscTrajectory(stub="tj_vars", delete_on_read=True) vecs = tj.interpolate_vecs(np.linspace(0, 24, 25)) # For more details about the problem behavior see the PETSc examples in the # examples repo. # make sure the inlet pressure is initially 5e5 Pa assert (pyo.value(vecs[str( m.fs.valve_1.control_volume.properties_in[24].pressure)][5]) == pytest.approx(5e5)) # make sure the inlet pressure ramped up to 6e5 Pa assert (pyo.value(vecs[str( m.fs.valve_1.control_volume.properties_in[24].pressure)][20]) == pytest.approx(6e5)) # make sure after the controller comes on the presure goes to the set point assert (pyo.value(vecs[str( m.fs.tank.control_volume.properties_out[24].pressure)][9]) == pytest.approx(3e5)) # make sure after ramping inlet pressure the tank pressure gets back to the # setpoint assert (pyo.value(vecs[str( m.fs.tank.control_volume.properties_out[24].pressure)][22]) == pytest.approx(3e5))