def test_shape(self): n = 100 bal = BalanceComp() bal.add_balance('x', shape=(n,)) tgt = IndepVarComp(name='y_tgt', val=4*np.ones(n)) exe = ExecComp('y=x**2', x=np.zeros(n), y=np.zeros(n)) model = Group() model.add_subsystem('tgt', tgt, promotes_outputs=['y_tgt']) model.add_subsystem('exe', exe) model.add_subsystem('bal', bal) model.connect('y_tgt', 'bal.rhs:x') model.connect('bal.x', 'exe.x') model.connect('exe.y', 'bal.lhs:x') model.linear_solver = DirectSolver(assemble_jac=True) model.nonlinear_solver = NewtonSolver(maxiter=100, iprint=0) prob = Problem(model) prob.setup() prob['bal.x'] = np.random.rand(n) prob.run_model() assert_almost_equal(prob['bal.x'], 2.0*np.ones(n), decimal=7)
def test_raise_no_error_on_singular(self): prob = Problem() model = prob.model comp = IndepVarComp() comp.add_output('dXdt:TAS', val=1.0) comp.add_output('accel_target', val=2.0) model.add_subsystem('des_vars', comp, promotes=['*']) teg = model.add_subsystem('thrust_equilibrium_group', subsys=Group()) teg.add_subsystem('dynamics', ExecComp('z = 2.0*thrust'), promotes=['*']) thrust_bal = BalanceComp() thrust_bal.add_balance(name='thrust', val=1207.1, lhs_name='dXdt:TAS', rhs_name='accel_target', eq_units='m/s**2', lower=-10.0, upper=10000.0) teg.add_subsystem(name='thrust_bal', subsys=thrust_bal, promotes_inputs=['dXdt:TAS', 'accel_target'], promotes_outputs=['thrust']) teg.linear_solver = DirectSolver(assemble_jac=False) teg.nonlinear_solver = NewtonSolver() teg.nonlinear_solver.options['solve_subsystems'] = True teg.nonlinear_solver.options['max_sub_solves'] = 1 teg.nonlinear_solver.options['atol'] = 1e-4 prob.setup(check=False) prob.set_solver_print(level=0) teg.linear_solver.options['err_on_singular'] = False prob.run_model()
def test_feature_scalar_with_default_mult(self): from numpy.testing import assert_almost_equal from openmdao.api import Problem, Group, IndepVarComp, ExecComp, NewtonSolver, \ DirectSolver, BalanceComp prob = Problem() bal = BalanceComp() bal.add_balance('x', use_mult=True, mult_val=2.0) tgt = IndepVarComp(name='y_tgt', val=4) exec_comp = ExecComp('y=x**2', x={'value': 1}, y={'value': 1}) prob.model.add_subsystem(name='target', subsys=tgt, promotes_outputs=['y_tgt']) prob.model.add_subsystem(name='exec', subsys=exec_comp) prob.model.add_subsystem(name='balance', subsys=bal) prob.model.connect('y_tgt', 'balance.rhs:x') prob.model.connect('balance.x', 'exec.x') prob.model.connect('exec.y', 'balance.lhs:x') prob.model.linear_solver = DirectSolver(assemble_jac=True) prob.model.nonlinear_solver = NewtonSolver(maxiter=100, iprint=0) prob.setup(check=False) # A reasonable initial guess to find the positive root. prob['balance.x'] = 1.0 prob.run_model() assert_almost_equal(prob['balance.x'], np.sqrt(2), decimal=7)
def test_renamed_vars(self): n = 1 prob = Problem(model=Group()) bal = BalanceComp() bal.add_balance('x', mult_name='MUL', lhs_name='XSQ', rhs_name='TARGETXSQ') tgt = IndepVarComp(name='y_tgt', val=4) mult_ivc = IndepVarComp(name='mult', val=2.0) exec_comp = ExecComp('y=x**2', x={'value': 1}, y={'value': 1}) prob.model.add_subsystem(name='target', subsys=tgt, promotes_outputs=['y_tgt']) prob.model.add_subsystem(name='mult_comp', subsys=mult_ivc, promotes_outputs=['mult']) prob.model.add_subsystem(name='exec', subsys=exec_comp) prob.model.add_subsystem(name='balance', subsys=bal) prob.model.connect('y_tgt', 'balance.TARGETXSQ') prob.model.connect('mult', 'balance.MUL') prob.model.connect('balance.x', 'exec.x') prob.model.connect('exec.y', 'balance.XSQ') prob.model.linear_solver = DirectSolver() prob.model.nonlinear_solver = NewtonSolver() prob.model.nonlinear_solver.options['maxiter'] = 100 prob.model.nonlinear_solver.options['iprint'] = 0 prob.model.jacobian = DenseJacobian() prob.setup() prob['balance.x'] = np.random.rand(n) prob.run_model() assert_almost_equal(prob['balance.x'], np.sqrt(2), decimal=7) np.set_printoptions(linewidth=1024) cpd = prob.check_partials() for (of, wrt) in cpd['balance']: assert_almost_equal(cpd['balance'][of, wrt]['abs error'], 0.0, decimal=5)
def test_vectorized_with_mult(self): n = 100 prob = Problem(model=Group()) bal = BalanceComp() bal.add_balance('x', val=np.ones(n), use_mult=True) tgt = IndepVarComp(name='y_tgt', val=4 * np.ones(n)) mult_ivc = IndepVarComp(name='mult', val=2.0 * np.ones(n)) exec_comp = ExecComp('y=x**2', x={'value': np.ones(n)}, y={'value': np.ones(n)}) prob.model.add_subsystem(name='target', subsys=tgt, promotes_outputs=['y_tgt']) prob.model.add_subsystem(name='mult_comp', subsys=mult_ivc, promotes_outputs=['mult']) prob.model.add_subsystem(name='exec', subsys=exec_comp) prob.model.add_subsystem(name='balance', subsys=bal) prob.model.connect('y_tgt', 'balance.rhs:x') prob.model.connect('mult', 'balance.mult:x') prob.model.connect('balance.x', 'exec.x') prob.model.connect('exec.y', 'balance.lhs:x') prob.model.linear_solver = DirectSolver() prob.model.nonlinear_solver = NewtonSolver() prob.model.nonlinear_solver.options['maxiter'] = 100 prob.model.nonlinear_solver.options['iprint'] = 0 prob.model.jacobian = DenseJacobian() prob.setup() prob['balance.x'] = np.random.rand(n) prob.run_model() assert_almost_equal(prob['balance.x'], np.sqrt(2), decimal=7) with printoptions(linewidth=1024): cpd = prob.check_partials() for (of, wrt) in cpd['balance']: assert_almost_equal(cpd['balance'][of, wrt]['abs error'], 0.0, decimal=5)
def test_scalar_example(self): prob = Problem(model=Group()) bal = BalanceComp() bal.add_balance('x', val=1.0) tgt = IndepVarComp(name='y_tgt', val=2) exec_comp = ExecComp('y=x**2') prob.model.add_subsystem(name='target', subsys=tgt, promotes_outputs=['y_tgt']) prob.model.add_subsystem(name='exec', subsys=exec_comp) prob.model.add_subsystem(name='balance', subsys=bal) prob.model.connect('y_tgt', 'balance.rhs:x') prob.model.connect('balance.x', 'exec.x') prob.model.connect('exec.y', 'balance.lhs:x') # do one test in an unconverged state, to capture accuracy of partials prob.setup() prob[ 'y_tgt'] = 100000 #set rhs and lhs to very different values. Trying to capture some derivatives wrt prob['exec.y'] = .001 prob.run_model() cpd = prob.check_partials() for (of, wrt) in cpd['balance']: assert_almost_equal(cpd['balance'][of, wrt]['abs error'], 0.0, decimal=5) # set an actual solver, and re-setup. Then check derivatives at a converged point prob.model.linear_solver = DirectSolver() prob.model.nonlinear_solver = NewtonSolver() prob.setup() prob.run_model() assert_almost_equal(prob['balance.x'], np.sqrt(2), decimal=7) np.set_printoptions(linewidth=1024) cpd = prob.check_partials() for (of, wrt) in cpd['balance']: assert_almost_equal(cpd['balance'][of, wrt]['abs error'], 0.0, decimal=5)
def test_debug_after_raised_error(self): prob = Problem() model = prob.model comp = IndepVarComp() comp.add_output('dXdt:TAS', val=1.0) comp.add_output('accel_target', val=2.0) model.add_subsystem('des_vars', comp, promotes=['*']) teg = model.add_subsystem('thrust_equilibrium_group', subsys=Group()) teg.add_subsystem('dynamics', ExecComp('z = 2.0*thrust'), promotes=['*']) thrust_bal = BalanceComp() thrust_bal.add_balance(name='thrust', val=1207.1, lhs_name='dXdt:TAS', rhs_name='accel_target', eq_units='m/s**2', lower=-10.0, upper=10000.0) teg.add_subsystem(name='thrust_bal', subsys=thrust_bal, promotes_inputs=['dXdt:TAS', 'accel_target'], promotes_outputs=['thrust']) teg.linear_solver = DirectSolver() teg.nonlinear_solver = NewtonSolver() teg.nonlinear_solver.options['solve_subsystems'] = True teg.nonlinear_solver.options['max_sub_solves'] = 1 teg.nonlinear_solver.options['atol'] = 1e-4 teg.nonlinear_solver.options['debug_print'] = True prob.setup(check=False) prob.set_solver_print(level=0) stdout = sys.stdout strout = StringIO() sys.stdout = strout with self.assertRaises(RuntimeError) as cm: prob.run_model() sys.stdout = stdout output = strout.getvalue() target = "'thrust_equilibrium_group.thrust_bal.thrust'" self.assertTrue(target in output, msg=target + "NOT FOUND IN" + output) # Make sure exception is unchanged. expected_msg = "Singular entry found in 'thrust_equilibrium_group' for row associated with state/residual 'thrust'." self.assertEqual(expected_msg, str(cm.exception))
def test_renamed_vars(self): n = 1 prob = Problem(model=Group(assembled_jac_type='dense')) bal = BalanceComp() bal.add_balance('x', use_mult=True, mult_name='MUL', lhs_name='XSQ', rhs_name='TARGETXSQ') tgt = IndepVarComp(name='y_tgt', val=4) mult_ivc = IndepVarComp(name='mult', val=2.0) exec_comp = ExecComp('y=x**2', x={'value': 1}, y={'value': 1}) prob.model.add_subsystem(name='target', subsys=tgt, promotes_outputs=['y_tgt']) prob.model.add_subsystem(name='mult_comp', subsys=mult_ivc, promotes_outputs=['mult']) prob.model.add_subsystem(name='exec', subsys=exec_comp) prob.model.add_subsystem(name='balance', subsys=bal) prob.model.connect('y_tgt', 'balance.TARGETXSQ') prob.model.connect('mult', 'balance.MUL') prob.model.connect('balance.x', 'exec.x') prob.model.connect('exec.y', 'balance.XSQ') prob.model.linear_solver = DirectSolver(assemble_jac=True) prob.model.nonlinear_solver = NewtonSolver(maxiter=100, iprint=0) prob.setup() prob['balance.x'] = np.random.rand(n) prob.run_model() assert_almost_equal(prob['balance.x'], np.sqrt(2), decimal=7) cpd = prob.check_partials(out_stream=None) for (of, wrt) in cpd['balance']: assert_almost_equal(cpd['balance'][of, wrt]['abs error'], 0.0, decimal=5)
def test_feature_scalar(self): from numpy.testing import assert_almost_equal from openmdao.api import Problem, Group, IndepVarComp, ExecComp, NewtonSolver, DirectSolver, DenseJacobian, BalanceComp n = 1 prob = Problem(model=Group()) bal = BalanceComp() bal.add_balance('x') tgt = IndepVarComp(name='y_tgt', val=4) mult_ivc = IndepVarComp(name='mult', val=2.0) exec_comp = ExecComp('y=x**2', x={'value': 1}, y={'value': 1}) prob.model.add_subsystem(name='target', subsys=tgt, promotes_outputs=['y_tgt']) prob.model.add_subsystem(name='mult_comp', subsys=mult_ivc, promotes_outputs=['mult']) prob.model.add_subsystem(name='exec', subsys=exec_comp) prob.model.add_subsystem(name='balance', subsys=bal) prob.model.connect('y_tgt', 'balance.rhs:x') prob.model.connect('mult', 'balance.mult:x') prob.model.connect('balance.x', 'exec.x') prob.model.connect('exec.y', 'balance.lhs:x') prob.model.linear_solver = DirectSolver() prob.model.nonlinear_solver = NewtonSolver() prob.model.nonlinear_solver.options['maxiter'] = 100 prob.model.nonlinear_solver.options['iprint'] = 0 prob.model.jacobian = DenseJacobian() prob.setup(check=False) # A reasonable initial guess to find the positive root. prob['balance.x'] = 1.0 prob.run_model() print('x = ', prob['balance.x']) assert_almost_equal(prob['balance.x'], np.sqrt(2), decimal=7)
def test_scalar_with_guess_func(self): n = 1 prob = Problem(model=Group()) bal = BalanceComp() bal.add_balance( 'x', guess_func=lambda inputs, resids: np.sqrt(inputs['rhs:x'])) tgt = IndepVarComp(name='y_tgt', val=4) exec_comp = ExecComp('y=x**2', x={'value': 1}, y={'value': 1}) prob.model.add_subsystem(name='target', subsys=tgt, promotes_outputs=['y_tgt']) prob.model.add_subsystem(name='exec', subsys=exec_comp) prob.model.add_subsystem(name='balance', subsys=bal) prob.model.connect('y_tgt', 'balance.rhs:x') prob.model.connect('balance.x', 'exec.x') prob.model.connect('exec.y', 'balance.lhs:x') prob.model.linear_solver = DirectSolver() prob.model.nonlinear_solver = NewtonSolver() prob.model.nonlinear_solver.options['maxiter'] = 100 prob.model.nonlinear_solver.options['iprint'] = 0 prob.model.jacobian = DenseJacobian() prob.setup() prob['balance.x'] = np.random.rand(n) prob.run_model() assert_almost_equal(prob['balance.x'], 2.0, decimal=7) with printoptions(linewidth=1024): cpd = prob.check_partials() for (of, wrt) in cpd['balance']: assert_almost_equal(cpd['balance'][of, wrt]['abs error'], 0.0, decimal=5)
def test_scalar_example(self): prob = Problem(model=Group()) bal = BalanceComp() bal.add_balance('x', val=1.0) tgt = IndepVarComp(name='y_tgt', val=2) exec_comp = ExecComp('y=x**2') prob.model.add_subsystem(name='target', subsys=tgt, promotes_outputs=['y_tgt']) prob.model.add_subsystem(name='exec', subsys=exec_comp) prob.model.add_subsystem(name='balance', subsys=bal) prob.model.connect('y_tgt', 'balance.rhs:x') prob.model.connect('balance.x', 'exec.x') prob.model.connect('exec.y', 'balance.lhs:x') # do one test in an unconverged state, to capture accuracy of partials prob.setup() prob['y_tgt'] = 100000 #set rhs and lhs to very different values. Trying to capture some derivatives wrt prob['exec.y'] = .001 prob.run_model() cpd = prob.check_partials() for (of, wrt) in cpd['balance']: assert_almost_equal(cpd['balance'][of, wrt]['abs error'], 0.0, decimal=5) # set an actual solver, and re-setup. Then check derivatives at a converged point prob.model.linear_solver = DirectSolver() prob.model.nonlinear_solver = NewtonSolver() prob.setup() prob.run_model() assert_almost_equal(prob['balance.x'], np.sqrt(2), decimal=7) np.set_printoptions(linewidth=1024) cpd = prob.check_partials() for (of, wrt) in cpd['balance']: assert_almost_equal(cpd['balance'][of, wrt]['abs error'], 0.0, decimal=5)
def test_renamed_vars(self): n = 1 prob = Problem(model=Group()) bal = BalanceComp() bal.add_balance('x', use_mult=True, mult_name='MUL', lhs_name='XSQ', rhs_name='TARGETXSQ') tgt = IndepVarComp(name='y_tgt', val=4) mult_ivc = IndepVarComp(name='mult', val=2.0) exec_comp = ExecComp('y=x**2', x={'value': 1}, y={'value': 1}) prob.model.add_subsystem(name='target', subsys=tgt, promotes_outputs=['y_tgt']) prob.model.add_subsystem(name='mult_comp', subsys=mult_ivc, promotes_outputs=['mult']) prob.model.add_subsystem(name='exec', subsys=exec_comp) prob.model.add_subsystem(name='balance', subsys=bal) prob.model.connect('y_tgt', 'balance.TARGETXSQ') prob.model.connect('mult', 'balance.MUL') prob.model.connect('balance.x', 'exec.x') prob.model.connect('exec.y', 'balance.XSQ') prob.model.linear_solver = DirectSolver() prob.model.nonlinear_solver = NewtonSolver() prob.model.nonlinear_solver.options['maxiter'] = 100 prob.model.nonlinear_solver.options['iprint'] = 0 prob.model.jacobian = DenseJacobian() prob.setup() prob['balance.x'] = np.random.rand(n) prob.run_model() assert_almost_equal(prob['balance.x'], np.sqrt(2), decimal=7) np.set_printoptions(linewidth=1024) cpd = prob.check_partials() for (of, wrt) in cpd['balance']: assert_almost_equal(cpd['balance'][of, wrt]['abs error'], 0.0, decimal=5)
def test_scalar_with_guess_func_additional_input(self): n = 1 prob = Problem(model=Group()) bal = BalanceComp() bal.add_balance('x', guess_func=lambda inputs, resids: inputs['guess_x']) bal.add_input('guess_x', val=0.0) ivc = IndepVarComp() ivc.add_output(name='y_tgt', val=4) ivc.add_output(name='guess_x', val=2.5) exec_comp = ExecComp('y=x**2', x={'value': 1}, y={'value': 1}) prob.model.add_subsystem(name='ivc', subsys=ivc, promotes_outputs=['y_tgt', 'guess_x']) prob.model.add_subsystem(name='exec', subsys=exec_comp) prob.model.add_subsystem(name='balance', subsys=bal) prob.model.connect('guess_x', 'balance.guess_x') prob.model.connect('y_tgt', 'balance.rhs:x') prob.model.connect('balance.x', 'exec.x') prob.model.connect('exec.y', 'balance.lhs:x') prob.model.linear_solver = DirectSolver() prob.model.nonlinear_solver = NewtonSolver() prob.model.nonlinear_solver.options['maxiter'] = 100 prob.model.nonlinear_solver.options['iprint'] = 0 prob.model.jacobian = DenseJacobian() prob.setup() prob['balance.x'] = np.random.rand(n) prob.run_model() assert_almost_equal(prob['balance.x'], 2.0, decimal=7) np.set_printoptions(linewidth=1024) cpd = prob.check_partials() for (of, wrt) in cpd['balance']: assert_almost_equal(cpd['balance'][of, wrt]['abs error'], 0.0, decimal=5)
def test_vectorized_no_normalization(self): n = 100 prob = Problem(model=Group(assembled_jac_type='dense')) bal = BalanceComp() bal.add_balance('x', val=np.ones(n), normalize=False) tgt = IndepVarComp(name='y_tgt', val=1.7 * np.ones(n)) exec_comp = ExecComp('y=x**2', x={'value': np.ones(n)}, y={'value': np.ones(n)}) prob.model.add_subsystem(name='target', subsys=tgt, promotes_outputs=['y_tgt']) prob.model.add_subsystem(name='exec', subsys=exec_comp) prob.model.add_subsystem(name='balance', subsys=bal) prob.model.connect('y_tgt', 'balance.rhs:x') prob.model.connect('balance.x', 'exec.x') prob.model.connect('exec.y', 'balance.lhs:x') prob.model.linear_solver = DirectSolver(assemble_jac=True) prob.model.nonlinear_solver = NewtonSolver(maxiter=100, iprint=0) prob.setup() prob['balance.x'] = np.random.rand(n) prob.run_model() assert_almost_equal(prob['balance.x'], np.sqrt(1.7), decimal=7) with printoptions(linewidth=1024): cpd = prob.check_partials() for (of, wrt) in cpd['balance']: assert_almost_equal(cpd['balance'][of, wrt]['abs error'], 0.0, decimal=5)
def test_feature_scalar(self): from numpy.testing import assert_almost_equal from openmdao.api import Problem, Group, IndepVarComp, ExecComp, NewtonSolver, DirectSolver, DenseJacobian, BalanceComp n = 1 prob = Problem(model=Group()) bal = BalanceComp() bal.add_balance('x', use_mult=True) tgt = IndepVarComp(name='y_tgt', val=4) mult_ivc = IndepVarComp(name='mult', val=2.0) exec_comp = ExecComp('y=x**2', x={'value': 1}, y={'value': 1}) prob.model.add_subsystem(name='target', subsys=tgt, promotes_outputs=['y_tgt']) prob.model.add_subsystem(name='mult_comp', subsys=mult_ivc, promotes_outputs=['mult']) prob.model.add_subsystem(name='exec', subsys=exec_comp) prob.model.add_subsystem(name='balance', subsys=bal) prob.model.connect('y_tgt', 'balance.rhs:x') prob.model.connect('mult', 'balance.mult:x') prob.model.connect('balance.x', 'exec.x') prob.model.connect('exec.y', 'balance.lhs:x') prob.model.linear_solver = DirectSolver() prob.model.nonlinear_solver = NewtonSolver() prob.model.nonlinear_solver.options['maxiter'] = 100 prob.model.nonlinear_solver.options['iprint'] = 0 prob.model.jacobian = DenseJacobian() prob.setup(check=False) # A reasonable initial guess to find the positive root. prob['balance.x'] = 1.0 prob.run_model() print('x = ', prob['balance.x']) assert_almost_equal(prob['balance.x'], np.sqrt(2), decimal=7)
def setup(self): num_nodes = self.options['num_nodes'] num_battery = self.options['num_battery'] num_motor = self.options['num_motor'] self.add_subsystem(name='pwr_balance', subsys=BalanceComp(name='I_Li', val=1.0 * np.ones(num_nodes), rhs_name='pwr_out_batt', lhs_name='P_pack', units='A', eq_units='W', lower=0.0, upper=50.)) self.add_subsystem('battery', Battery(num_nodes=num_nodes, n_parallel=num_battery), promotes_inputs=['SOC'], promotes_outputs=['dXdt:SOC']) self.add_subsystem( 'motors', MotorsStaticGearboxPower(num_nodes=num_nodes, n_parallel=num_motor)) self.connect('battery.P_pack', 'pwr_balance.P_pack') self.connect('motors.power_in_motor', 'pwr_balance.pwr_out_batt') self.connect('pwr_balance.I_Li', 'battery.I_Li') self.connect('battery.I_pack', 'motors.current_in_motor') self.nonlinear_solver = NewtonSolver() self.nonlinear_solver.options['maxiter'] = 20 self.linear_solver = DirectSolver()
def test_create_on_init(self): prob = Problem(model=Group()) bal = BalanceComp('x', val=1.0) tgt = IndepVarComp(name='y_tgt', val=2) exec_comp = ExecComp('y=x**2') prob.model.add_subsystem(name='target', subsys=tgt, promotes_outputs=['y_tgt']) prob.model.add_subsystem(name='exec', subsys=exec_comp) prob.model.add_subsystem(name='balance', subsys=bal) prob.model.connect('y_tgt', 'balance.rhs:x') prob.model.connect('balance.x', 'exec.x') prob.model.connect('exec.y', 'balance.lhs:x') prob.model.linear_solver = DirectSolver() prob.model.nonlinear_solver = NewtonSolver() prob.setup() prob.run_model() assert_almost_equal(prob['balance.x'], np.sqrt(2), decimal=7) np.set_printoptions(linewidth=1024) cpd = prob.check_partials() for (of, wrt) in cpd['balance']: assert_almost_equal(cpd['balance'][of, wrt]['abs error'], 0.0, decimal=5)
def setup(self): shape = self.options['shape'] bal = self.add_subsystem('alpha_upper_balance', BalanceComp()) bal.add_balance('Mu_1') comp = ExecComp( 'nu_1 = power((gamma+1)/(gamma-1),0.5) * ' + '180/pi * arctan(power((gamma-1)/(gamma+1)*(Mu_1**2-1),0.5)) - ' + '180/pi * arctan(power((Mu_1**2-1),0.5))', shape=shape) self.add_subsystem('front_upper_PM_expansion_comp', comp, promotes=['*']) comp = ExecComp( 'nu_inf = power((gamma+1)/(gamma-1),0.5) * ' + '180/pi * arctan(power((gamma-1)/(gamma+1)*(Mu_inf**2-1),0.5)) - ' + '180/pi * arctan(power((Mu_inf**2-1),0.5))', shape=shape) self.add_subsystem('front_freestream_PM_expansion_comp', comp, promotes=['*']) comp = ExecComp('delta_nu_upper = nu_1 - nu_inf', shape=shape) self.add_subsystem('front_PM_expansion_delta_comp', comp, promotes=['*']) # NOTES: # check whether arctan works with degrees or radians; we need result # in degrees since the PM expansion equation operates using degrees
def setup(self): nn = self.options['num_nodes'] self.add_subsystem('aero', subsys=AerodynamicsGroup(num_nodes=nn)) self.add_subsystem( 'thrust_eq_comp', subsys=ThrustEquilibriumComp(num_nodes=nn), promotes_inputs=['q', 'S', 'gam', 'alpha', 'W_total'], promotes_outputs=['CT']) self.add_subsystem( 'lift_eq_comp', subsys=LiftEquilibriumComp(num_nodes=nn), promotes_inputs=['q', 'S', 'gam', 'alpha', 'W_total', 'CT'], promotes_outputs=['CL_eq']) bal = self.add_subsystem(name='alpha_eta_balance', subsys=BalanceComp(), promotes_outputs=['alpha', 'eta']) self.connect('alpha', ('aero.alpha')) self.connect('eta', ('aero.eta')) bal.add_balance('alpha', units='rad', eq_units=None, lhs_name='CL_eq', rhs_name='CL', val=0.01 * np.ones(nn), lower=-20, upper=30, res_ref=1.0) bal.add_balance('eta', units='rad', val=0.01 * np.ones(nn), eq_units=None, lhs_name='CM', lower=-30, upper=30, res_ref=1.0) self.connect('aero.CL', 'alpha_eta_balance.CL') self.connect('aero.CD', 'thrust_eq_comp.CD') self.connect('aero.CM', 'alpha_eta_balance.CM') self.connect('CL_eq', ('alpha_eta_balance.CL_eq')) self.linear_solver = DirectSolver() self.nonlinear_solver = NewtonSolver() self.nonlinear_solver.options['atol'] = 1e-14 self.nonlinear_solver.options['rtol'] = 1e-14 self.nonlinear_solver.options['solve_subsystems'] = True self.nonlinear_solver.options['err_on_maxiter'] = True self.nonlinear_solver.options['max_sub_solves'] = 10 self.nonlinear_solver.options['maxiter'] = 150 self.nonlinear_solver.options['iprint'] = -1 # self.nonlinear_solver.linesearch = ArmijoGoldsteinLS() self.nonlinear_solver.linesearch = BoundsEnforceLS() self.nonlinear_solver.linesearch.options['print_bound_enforce'] = True
def setup(self): nn = self.options['num_nodes'] ivcomp = self.add_subsystem('const_settings', IndepVarComp(), promotes_outputs=["*"]) ivcomp.add_output('propulsor_active', val=np.ones(nn)) ivcomp.add_output('braking', val=np.zeros(nn)) # TODO feet fltcond|Ueas as control param ivcomp.add_output('fltcond|Ueas',val=np.ones((nn,))*90, units='m/s') # TODO feed fltcond|vs as control param ivcomp.add_output('fltcond|vs',val=np.ones((nn,))*1, units='m/s') ivcomp.add_output('zero_accel',val=np.zeros((nn,)),units='m/s**2') # TODO take out the integrator integ = self.add_subsystem('ode_integ', Integrator(num_nodes=nn, diff_units='s', time_setup='duration', method='simpson'), promotes_inputs=['fltcond|vs', 'fltcond|groundspeed'], promotes_outputs=['fltcond|h', 'range']) integ.add_integrand('fltcond|h', rate_name='fltcond|vs', val=1.0, units='m') # TODO Feed fltcond|h as state self.add_subsystem('atmos', ComputeAtmosphericProperties(num_nodes=nn, true_airspeed_in=False), promotes_inputs=['*'], promotes_outputs=['*']) self.add_subsystem('gs',Groundspeeds(num_nodes=nn),promotes_inputs=['*'],promotes_outputs=['*']) # add the user-defined aircraft model # TODO Can I promote up ac| quantities? self.add_subsystem('acmodel',self.options['aircraft_model'](num_nodes=nn, flight_phase=self.options['flight_phase']),promotes_inputs=['*'],promotes_outputs=['*']) self.add_subsystem('clcomp',SteadyFlightCL(num_nodes=nn), promotes_inputs=['*'],promotes_outputs=['*']) self.add_subsystem('lift',Lift(num_nodes=nn), promotes_inputs=['*'],promotes_outputs=['*']) self.add_subsystem('haccel',HorizontalAcceleration(num_nodes=nn), promotes_inputs=['*'],promotes_outputs=['*']) # TODO add range as a state integ.add_integrand('range', rate_name='fltcond|groundspeed', val=1.0, units='m') self.add_subsystem('steadyflt',BalanceComp(name='throttle',val=np.ones((nn,))*0.5,lower=0.01,upper=2.0,units=None,normalize=False,eq_units='m/s**2',rhs_name='accel_horiz',lhs_name='zero_accel',rhs_val=np.zeros((nn,))), promotes_inputs=['accel_horiz','zero_accel'],promotes_outputs=['throttle']) # TODO still needs a Newton solver
def setup(self): thermo_spec = species_data.janaf self.add_subsystem( 'fc', FlightConditions(thermo_data=thermo_spec, elements=AIR_MIX)) self.add_subsystem( 'inlet', Inlet(design=True, thermo_data=thermo_spec, elements=AIR_MIX)) self.add_subsystem( 'fan', Compressor(thermo_data=thermo_spec, elements=AIR_MIX, design=True)) self.add_subsystem('nozz', Nozzle(thermo_data=thermo_spec, elements=AIR_MIX)) self.add_subsystem('perf', Performance(num_nozzles=1, num_burners=0)) self.add_subsystem('shaft', IndepVarComp('Nmech', 1., units='rpm')) self.add_subsystem('pwr_balance', BalanceComp('W', units='lbm/s', eq_units='hp', val=50., lower=1., upper=500.), promotes_inputs=[('rhs:W', 'pwr_target')]) # self.set_order(['pwr_balance', 'pwr_target', 'fc', 'inlet', 'shaft', 'fan', 'nozz', 'perf']) connect_flow(self, 'fc.Fl_O', 'inlet.Fl_I') connect_flow(self, 'inlet.Fl_O', 'fan.Fl_I') connect_flow(self, 'fan.Fl_O', 'nozz.Fl_I') self.connect('shaft.Nmech', 'fan.Nmech') self.connect('fc.Fl_O:stat:P', 'nozz.Ps_exhaust') self.connect('inlet.Fl_O:tot:P', 'perf.Pt2') self.connect('fan.Fl_O:tot:P', 'perf.Pt3') self.connect('inlet.F_ram', 'perf.ram_drag') self.connect('nozz.Fg', 'perf.Fg_0') self.connect('pwr_balance.W', 'fc.W') self.connect('fan.power', 'pwr_balance.lhs:W') newton = self.nonlinear_solver = NewtonSolver() newton.options['atol'] = 1e-12 newton.options['rtol'] = 1e-12 newton.options['iprint'] = 2 newton.options['maxiter'] = 10 newton.options['solve_subsystems'] = True newton.options['max_sub_solves'] = 10 # newton.linesearch = BoundsEnforceLS() newton.linesearch.options['bound_enforcement'] = 'scalar' # newton.linesearch.options['print_bound_enforce'] = True # newton.linesearch.options['iprint'] = -1 # self.linear_solver = DirectSolver(assemble_jac=True)
def test_scalar_with_mult(self): n = 1 prob = Problem(model=Group(assembled_jac_type='dense')) bal = BalanceComp() bal.add_balance('x', use_mult=True) tgt = IndepVarComp(name='y_tgt', val=4) mult_ivc = IndepVarComp(name='mult', val=2.0) exec_comp = ExecComp('y=x**2', x={'value': 1}, y={'value': 1}) prob.model.add_subsystem(name='target', subsys=tgt, promotes_outputs=['y_tgt']) prob.model.add_subsystem(name='mult_comp', subsys=mult_ivc, promotes_outputs=['mult']) prob.model.add_subsystem(name='exec', subsys=exec_comp) prob.model.add_subsystem(name='balance', subsys=bal) prob.model.connect('y_tgt', 'balance.rhs:x') prob.model.connect('mult', 'balance.mult:x') prob.model.connect('balance.x', 'exec.x') prob.model.connect('exec.y', 'balance.lhs:x') prob.model.linear_solver = DirectSolver(assemble_jac=True) prob.model.nonlinear_solver = NewtonSolver(maxiter=100, iprint=0) prob.setup() prob['balance.x'] = np.random.rand(n) prob.run_model() assert_almost_equal(prob['balance.x'], np.sqrt(2), decimal=7) with printoptions(linewidth=1024): cpd = prob.check_partials() for (of, wrt) in cpd['balance']: assert_almost_equal(cpd['balance'][of, wrt]['abs error'], 0.0, decimal=5)
def test_scalar_guess_func_using_outputs(self): # Implicitly solve -(ax^2 + bx) = c using a BalanceComp. # For a=1, b=-4 and c=3, there are solutions at x=1 and x=3. # Verify that we can set the guess value (and target a solution) based on outputs. ind = IndepVarComp() ind.add_output('a', 1) ind.add_output('b', -4) ind.add_output('c', 3) lhs = ExecComp('lhs=-(a*x**2+b*x)') bal = BalanceComp() def guess_function(inputs, outputs, residuals): if outputs['x'] < 0: return 5. else: return 0. bal.add_balance(name='x', rhs_name='c', guess_func=guess_function) model = Group() model.add_subsystem('ind_comp', ind, promotes_outputs=['a', 'b', 'c']) model.add_subsystem('lhs_comp', lhs, promotes_inputs=['a', 'b', 'x']) model.add_subsystem('bal_comp', bal, promotes_inputs=['c'], promotes_outputs=['x']) model.connect('lhs_comp.lhs', 'bal_comp.lhs:x') model.linear_solver = DirectSolver() model.nonlinear_solver = NewtonSolver(maxiter=1000, iprint=0) prob = Problem(model) prob.setup() # initial value of 'x' less than zero, guess should steer us to solution of 3. prob['bal_comp.x'] = -1 prob.run_model() assert_almost_equal(prob['bal_comp.x'], 3.0, decimal=7) # initial value of 'x' greater than zero, guess should steer us to solution of 1. prob['bal_comp.x'] = 99 prob.run_model() assert_almost_equal(prob['bal_comp.x'], 1.0, decimal=7)
def test_vectorized(self): n = 100 prob = Problem(model=Group()) bal = BalanceComp() bal.add_balance('x', val=np.ones(n)) tgt = IndepVarComp(name='y_tgt', val=4*np.ones(n)) exec_comp = ExecComp('y=x**2', x={'value': np.ones(n)}, y={'value': np.ones(n)}) prob.model.add_subsystem(name='target', subsys=tgt, promotes_outputs=['y_tgt']) prob.model.add_subsystem(name='exec', subsys=exec_comp) prob.model.add_subsystem(name='balance', subsys=bal) prob.model.connect('y_tgt', 'balance.rhs:x') prob.model.connect('balance.x', 'exec.x') prob.model.connect('exec.y', 'balance.lhs:x') prob.model.linear_solver = DirectSolver() prob.model.nonlinear_solver = NewtonSolver() prob.model.nonlinear_solver.options['maxiter'] = 100 prob.model.nonlinear_solver.options['iprint'] = 0 prob.model.jacobian = DenseJacobian() prob.setup() prob['balance.x'] = np.random.rand(n) prob.run_model() assert_almost_equal(prob['balance.x'], 2.0, decimal=7) np.set_printoptions(linewidth=1024) cpd = prob.check_partials() for (of, wrt) in cpd['balance']: assert_almost_equal(cpd['balance'][of, wrt]['abs error'], 0.0, decimal=5)
def test_raise_error_on_singular_with_densejac(self): prob = Problem() model = prob.model comp = IndepVarComp() comp.add_output('dXdt:TAS', val=1.0) comp.add_output('accel_target', val=2.0) model.add_subsystem('des_vars', comp, promotes=['*']) teg = model.add_subsystem('thrust_equilibrium_group', subsys=Group()) teg.add_subsystem('dynamics', ExecComp('z = 2.0*thrust'), promotes=['*']) thrust_bal = BalanceComp() thrust_bal.add_balance(name='thrust', val=1207.1, lhs_name='dXdt:TAS', rhs_name='accel_target', eq_units='m/s**2', lower=-10.0, upper=10000.0) teg.add_subsystem(name='thrust_bal', subsys=thrust_bal, promotes_inputs=['dXdt:TAS', 'accel_target'], promotes_outputs=['thrust']) teg.linear_solver = DirectSolver(assemble_jac=True) teg.options['assembled_jac_type'] = 'dense' teg.nonlinear_solver = NewtonSolver() teg.nonlinear_solver.options['solve_subsystems'] = True teg.nonlinear_solver.options['max_sub_solves'] = 1 teg.nonlinear_solver.options['atol'] = 1e-4 prob.setup(check=False) prob.set_solver_print(level=0) with self.assertRaises(RuntimeError) as cm: prob.run_model() expected_msg = "Singular entry found in 'thrust_equilibrium_group' for column associated with state/residual 'thrust'." self.assertEqual(expected_msg, str(cm.exception))
def test_complex_step(self): n = 1 prob = Problem(model=Group(assembled_jac_type='dense')) bal = BalanceComp() bal.add_balance('x') tgt = IndepVarComp(name='y_tgt', val=4) exec_comp = ExecComp('y=x**2', x={'value': 1}, y={'value': 1}) prob.model.add_subsystem(name='target', subsys=tgt, promotes_outputs=['y_tgt']) prob.model.add_subsystem(name='exec', subsys=exec_comp) prob.model.add_subsystem(name='balance', subsys=bal) prob.model.connect('y_tgt', 'balance.rhs:x') prob.model.connect('balance.x', 'exec.x') prob.model.connect('exec.y', 'balance.lhs:x') prob.model.linear_solver = DirectSolver(assemble_jac=True) prob.model.nonlinear_solver = NewtonSolver(maxiter=100, iprint=0) prob.setup(force_alloc_complex=True) prob['balance.x'] = np.random.rand(n) prob.run_model() with warnings.catch_warnings(): warnings.filterwarnings(action="error", category=np.ComplexWarning) cpd = prob.check_partials(out_stream=None, method='cs') for (of, wrt) in cpd['balance']: assert_almost_equal(cpd['balance'][of, wrt]['abs error'], 0.0, decimal=10)
def setup(self): thermo_data = self.options['thermo_data'] elements = self.options['elements'] self.add_subsystem('fs', FlowStart(thermo_data=thermo_data, elements=elements), promotes_outputs=['Fl_O:*'], promotes_inputs=['W']) balance = BalanceComp() balance.add_balance('P', val=10., units='psi', eq_units='psi', lhs_name='Ps_computed', rhs_name='Ps', lower=1e-1) #guess_func=lambda inputs, resids: 5.) balance.add_balance('T', val=800., units='degR', eq_units='ft/s', lhs_name='V_computed', rhs_name='V', lower=1e-1) #guess_func=lambda inputs, resids: 400.) balance.add_balance('MN', val=.3, eq_units='inch**2', lhs_name='area_computed', rhs_name='area', lower=1e-6) #guess_func=lambda inputs, resids: .6) self.add_subsystem('balance', balance, promotes_inputs=['Ps', 'V', 'area']) self.connect('Fl_O:stat:P', 'balance.Ps_computed') self.connect('Fl_O:stat:V', 'balance.V_computed') self.connect('Fl_O:stat:area', 'balance.area_computed') self.connect('balance.P', 'fs.P') self.connect('balance.T', 'fs.T') self.connect('balance.MN', 'fs.MN') newton = self.nonlinear_solver = NewtonSolver() newton.options['solve_subsystems'] = True newton.options['maxiter'] = 10 # newton.linesearch = BoundsEnforceLS() # newton.linesearch.options['print_bound_enforce'] = True self.linear_solver = DirectSolver(assemble_jac=True)
def N3_MDP_verif_model(OD_statics=True): prob = Problem() prob.model = MPN3(order_add=['bal'], statics=OD_statics) prob.model.pyc_add_cycle_param('ext_ratio.core_Cv', 0.9999) prob.model.pyc_add_cycle_param('ext_ratio.byp_Cv', 0.9975) bal = prob.model.add_subsystem('bal', BalanceComp(), promotes_inputs=[ 'RTO_T4', ]) bal.add_balance('TOC_BPR', val=23.7281, units=None, eq_units=None) prob.model.connect('bal.TOC_BPR', 'TOC.splitter.BPR') prob.model.connect('CRZ.ext_ratio.ER', 'bal.lhs:TOC_BPR') bal.add_balance('TOC_W', val=820.95, units='lbm/s', eq_units='degR', rhs_name='RTO_T4') prob.model.connect('bal.TOC_W', 'TOC.fc.W') prob.model.connect('RTO.burner.Fl_O:tot:T', 'bal.lhs:TOC_W') bal.add_balance('CRZ_Fn_target', val=5514.4, units='lbf', eq_units='lbf', use_mult=True, mult_val=0.9, ref0=5000.0, ref=7000.0) prob.model.connect('bal.CRZ_Fn_target', 'CRZ.balance.rhs:FAR') prob.model.connect('TOC.perf.Fn', 'bal.lhs:CRZ_Fn_target') prob.model.connect('CRZ.perf.Fn', 'bal.rhs:CRZ_Fn_target') bal.add_balance('SLS_Fn_target', val=28620.8, units='lbf', eq_units='lbf', use_mult=True, mult_val=1.2553, ref0=28000.0, ref=30000.0) prob.model.connect('bal.SLS_Fn_target', 'SLS.balance.rhs:FAR') prob.model.connect('RTO.perf.Fn', 'bal.lhs:SLS_Fn_target') prob.model.connect('SLS.perf.Fn', 'bal.rhs:SLS_Fn_target') prob.model.set_input_defaults('RTO_T4', 3400.0, units='degR') return (prob)
def test_feature_scalar_with_default_mult(self): from numpy.testing import assert_almost_equal from openmdao.api import Problem, Group, IndepVarComp, ExecComp, NewtonSolver, \ DirectSolver, BalanceComp prob = Problem(model=Group(assembled_jac_type='dense')) bal = BalanceComp() bal.add_balance('x', use_mult=True, mult_val=2.0) tgt = IndepVarComp(name='y_tgt', val=4) exec_comp = ExecComp('y=x**2', x={'value': 1}, y={'value': 1}) prob.model.add_subsystem(name='target', subsys=tgt, promotes_outputs=['y_tgt']) prob.model.add_subsystem(name='exec', subsys=exec_comp) prob.model.add_subsystem(name='balance', subsys=bal) prob.model.connect('y_tgt', 'balance.rhs:x') prob.model.connect('balance.x', 'exec.x') prob.model.connect('exec.y', 'balance.lhs:x') prob.model.linear_solver = DirectSolver(assemble_jac=True) prob.model.nonlinear_solver = NewtonSolver(maxiter=100, iprint=0) prob.setup(check=False) # A reasonable initial guess to find the positive root. prob['balance.x'] = 1.0 prob.run_model() print('x = ', prob['balance.x']) assert_almost_equal(prob['balance.x'], np.sqrt(2), decimal=7)
def test_vectorized_no_normalization(self): n = 100 prob = Problem(model=Group(assembled_jac_type='dense')) bal = BalanceComp() bal.add_balance('x', val=np.ones(n), normalize=False) tgt = IndepVarComp(name='y_tgt', val=1.7*np.ones(n)) exec_comp = ExecComp('y=x**2', x={'value': np.ones(n)}, y={'value': np.ones(n)}) prob.model.add_subsystem(name='target', subsys=tgt, promotes_outputs=['y_tgt']) prob.model.add_subsystem(name='exec', subsys=exec_comp) prob.model.add_subsystem(name='balance', subsys=bal) prob.model.connect('y_tgt', 'balance.rhs:x') prob.model.connect('balance.x', 'exec.x') prob.model.connect('exec.y', 'balance.lhs:x') prob.model.linear_solver = DirectSolver(assemble_jac=True) prob.model.nonlinear_solver = NewtonSolver(maxiter=100, iprint=0) prob.setup() prob['balance.x'] = np.random.rand(n) prob.run_model() assert_almost_equal(prob['balance.x'], np.sqrt(1.7), decimal=7) cpd = prob.check_partials(out_stream=None) for (of, wrt) in cpd['balance']: assert_almost_equal(cpd['balance'][of, wrt]['abs error'], 0.0, decimal=5)
def test_scalar_with_guess_func_additional_input(self): model = Group(assembled_jac_type='dense') bal = BalanceComp() bal.add_balance('x') bal.add_input('guess_x', val=0.0) ivc = IndepVarComp() ivc.add_output(name='y_tgt', val=4) ivc.add_output(name='guess_x', val=2.5) exec_comp = ExecComp('y=x**2', x={'value': 1}, y={'value': 1}) model.add_subsystem(name='ivc', subsys=ivc, promotes_outputs=['y_tgt', 'guess_x']) model.add_subsystem(name='exec', subsys=exec_comp) model.add_subsystem(name='balance', subsys=bal) model.connect('guess_x', 'balance.guess_x') model.connect('y_tgt', 'balance.rhs:x') model.connect('balance.x', 'exec.x') model.connect('exec.y', 'balance.lhs:x') model.linear_solver = DirectSolver(assemble_jac=True) model.nonlinear_solver = NewtonSolver(maxiter=100, iprint=0) prob = Problem(model) prob.setup() # run problem without a guess function prob['balance.x'] = .5 prob.run_model() assert_almost_equal(prob['balance.x'], 2.0, decimal=7) iters_no_guess = model.nonlinear_solver._iter_count # run problem with same initial value and a guess function def guess_function(inputs, outputs, resids): outputs['x'] = inputs['guess_x'] bal.options['guess_func'] = guess_function prob['balance.x'] = .5 prob.run_model() assert_almost_equal(prob['balance.x'], 2.0, decimal=7) iters_with_guess = model.nonlinear_solver._iter_count # verify it converges faster with the guess function self.assertTrue(iters_with_guess < iters_no_guess)
def setup(self): shape = self.options['shape'] bal = self.add_subsystem('alpha_lower_balance', BalanceComp()) bal.add_balance('beta_2') comp = ExecComp('alpha_2 = 180/pi * arctan(' + '2*power(tan(beta_2 * pi/180),-1.0) * ' + '(power(Mu_inf*sin(beta_2 * pi/180),2.0) - 1.0) / ' + '(2 + Mu_inf**2 * (gamma + cos(2*beta_2 * pi/180))))', shape=shape) self.add_subsystem('front_lower_shock_angle_comp', comp, promotes=['*'])
def setup(self): thermo_data = self.options['thermo_data'] elements = self.options['elements'] self.add_subsystem('ambient', Ambient(), promotes=('alt', 'dTs')) # inputs conv = self.add_subsystem('conv', Group(), promotes=['*']) conv.add_subsystem('fs', FlowStart(thermo_data=thermo_data, elements=elements), promotes=['Fl_O:*', 'MN', 'W']) balance = conv.add_subsystem('balance', BalanceComp()) balance.add_balance('Tt', val=500.0, lower=1e-4, units='degR', desc='Total temperature', eq_units='degR') balance.add_balance('Pt', val=14.696, lower=1e-4, units='psi', desc='Total pressure', eq_units='psi') # sub.set_order(['fs','balance']) newton = conv.nonlinear_solver = NewtonSolver() newton.options['atol'] = 1e-10 newton.options['rtol'] = 1e-10 newton.options['maxiter'] = 10 newton.options['iprint'] = -1 newton.options['solve_subsystems'] = True newton.linesearch = BoundsEnforceLS() newton.linesearch.options['bound_enforcement'] = 'scalar' newton.linesearch.options['iprint'] = -1 # newton.linesearch.options['solve_subsystems'] = True conv.linear_solver = DirectSolver(assemble_jac=True) self.connect('ambient.Ps', 'balance.rhs:Pt') self.connect('ambient.Ts', 'balance.rhs:Tt') self.connect('balance.Pt', 'fs.P') self.connect('balance.Tt', 'fs.T') self.connect('Fl_O:stat:P', 'balance.lhs:Pt') self.connect('Fl_O:stat:T', 'balance.lhs:Tt')
def test_feature_vector(self): import numpy as np from numpy.testing import assert_almost_equal from openmdao.api import Problem, Group, ExecComp, NewtonSolver, DirectSolver, \ DenseJacobian, BalanceComp n = 100 prob = Problem(model=Group()) exec_comp = ExecComp('y=b*x+c', b={'value': np.random.uniform(0.01, 100, size=n)}, c={'value': np.random.rand(n)}, x={'value': np.zeros(n)}, y={'value': np.ones(n)}) prob.model.add_subsystem(name='exec', subsys=exec_comp) prob.model.add_subsystem(name='balance', subsys=BalanceComp('x', val=np.ones(n))) prob.model.connect('balance.x', 'exec.x') prob.model.connect('exec.y', 'balance.lhs:x') prob.model.linear_solver = DirectSolver() prob.model.nonlinear_solver = NewtonSolver() prob.model.nonlinear_solver.options['maxiter'] = 100 prob.model.nonlinear_solver.options['iprint'] = 0 prob.model.jacobian = DenseJacobian() prob.setup(check=False) prob['balance.x'] = np.random.rand(n) prob.run_model() b = prob['exec.b'] c = prob['exec.c'] assert_almost_equal(prob['balance.x'], -c / b, decimal=6) print('solution') print(prob['balance.x']) print('expected') print(-c / b)
def test_vectorized_with_default_mult(self): """ solve: 2 * x**2 = 4 expected solution: x=sqrt(2) """ n = 100 prob = Problem(model=Group(assembled_jac_type='dense')) bal = BalanceComp('x', val=np.ones(n), use_mult=True, mult_val=2.0) tgt = IndepVarComp(name='y_tgt', val=4 * np.ones(n)) exec_comp = ExecComp('y=x**2', x={'value': np.ones(n)}, y={'value': np.ones(n)}) prob.model.add_subsystem(name='target', subsys=tgt, promotes_outputs=['y_tgt']) prob.model.add_subsystem(name='exec', subsys=exec_comp) prob.model.add_subsystem(name='balance', subsys=bal) prob.model.connect('y_tgt', 'balance.rhs:x') prob.model.connect('balance.x', 'exec.x') prob.model.connect('exec.y', 'balance.lhs:x') prob.model.linear_solver = DirectSolver(assemble_jac=True) prob.model.nonlinear_solver = NewtonSolver(maxiter=100, iprint=0) prob.setup() prob['balance.x'] = np.random.rand(n) prob.run_model() assert_almost_equal(prob['balance.x'], np.sqrt(2), decimal=7) cpd = prob.check_partials(out_stream=None) for (of, wrt) in cpd['balance']: assert_almost_equal(cpd['balance'][of, wrt]['abs error'], 0.0, decimal=5)
def test_scalar_with_guess_func(self): n = 1 model = Group(assembled_jac_type='dense') def guess_function(inputs, outputs, residuals): outputs['x'] = np.sqrt(inputs['rhs:x']) bal = BalanceComp( 'x', guess_func=guess_function) # test guess_func as kwarg tgt = IndepVarComp(name='y_tgt', val=4) exec_comp = ExecComp('y=x**2', x={'value': 1}, y={'value': 1}) model.add_subsystem(name='target', subsys=tgt, promotes_outputs=['y_tgt']) model.add_subsystem(name='exec', subsys=exec_comp) model.add_subsystem(name='balance', subsys=bal) model.connect('y_tgt', 'balance.rhs:x') model.connect('balance.x', 'exec.x') model.connect('exec.y', 'balance.lhs:x') model.linear_solver = DirectSolver(assemble_jac=True) model.nonlinear_solver = NewtonSolver(maxiter=100, iprint=0) prob = Problem(model) prob.setup() prob['balance.x'] = np.random.rand(n) prob.run_model() assert_almost_equal(prob['balance.x'], 2.0, decimal=7) # should converge with no iteration due to the guess function self.assertEqual(model.nonlinear_solver._iter_count, 1) cpd = prob.check_partials(out_stream=None) for (of, wrt) in cpd['balance']: assert_almost_equal(cpd['balance'][of, wrt]['abs error'], 0.0, decimal=5)
def test_scalar_with_guess_func_additional_input(self): n = 1 prob = Problem(model=Group(assembled_jac_type='dense')) bal = BalanceComp() bal.add_balance('x', guess_func=lambda inputs, resids: inputs['guess_x']) bal.add_input('guess_x', val=0.0) ivc = IndepVarComp() ivc.add_output(name='y_tgt', val=4) ivc.add_output(name='guess_x', val=2.5) exec_comp = ExecComp('y=x**2', x={'value': 1}, y={'value': 1}) prob.model.add_subsystem(name='ivc', subsys=ivc, promotes_outputs=['y_tgt', 'guess_x']) prob.model.add_subsystem(name='exec', subsys=exec_comp) prob.model.add_subsystem(name='balance', subsys=bal) prob.model.connect('guess_x', 'balance.guess_x') prob.model.connect('y_tgt', 'balance.rhs:x') prob.model.connect('balance.x', 'exec.x') prob.model.connect('exec.y', 'balance.lhs:x') prob.model.linear_solver = DirectSolver(assemble_jac=True) prob.model.nonlinear_solver = NewtonSolver(maxiter=100, iprint=0) prob.setup() prob['balance.x'] = np.random.rand(n) prob.run_model() assert_almost_equal(prob['balance.x'], 2.0, decimal=7) with printoptions(linewidth=1024): cpd = prob.check_partials() for (of, wrt) in cpd['balance']: assert_almost_equal(cpd['balance'][of, wrt]['abs error'], 0.0, decimal=5)
def test_rhs_val(self): """ Test solution with a default RHS value and no connected RHS variable. """ n = 1 prob = Problem(model=Group()) bal = BalanceComp('x', rhs_val=4.0) exec_comp = ExecComp('y=x**2', x={'value': 1}, y={'value': 1}) prob.model.add_subsystem(name='exec', subsys=exec_comp) prob.model.add_subsystem(name='balance', subsys=bal) prob.model.connect('balance.x', 'exec.x') prob.model.connect('exec.y', 'balance.lhs:x') prob.model.linear_solver = DirectSolver() prob.model.nonlinear_solver = NewtonSolver() prob.model.nonlinear_solver.options['maxiter'] = 100 prob.model.nonlinear_solver.options['iprint'] = 0 prob.model.jacobian = DenseJacobian() prob.setup() prob['balance.x'] = np.random.rand(n) prob.run_model() assert_almost_equal(prob['balance.x'], 2.0, decimal=7) with printoptions(linewidth=1024): cpd = prob.check_partials() for (of, wrt) in cpd['balance']: assert_almost_equal(cpd['balance'][of, wrt]['abs error'], 0.0, decimal=5)
def test_create_on_init(self): prob = Problem(model=Group()) bal = BalanceComp('x', val=1.0) tgt = IndepVarComp(name='y_tgt', val=2) exec_comp = ExecComp('y=x**2') prob.model.add_subsystem(name='target', subsys=tgt, promotes_outputs=['y_tgt']) prob.model.add_subsystem(name='exec', subsys=exec_comp) prob.model.add_subsystem(name='balance', subsys=bal) prob.model.connect('y_tgt', 'balance.rhs:x') prob.model.connect('balance.x', 'exec.x') prob.model.connect('exec.y', 'balance.lhs:x') prob.model.linear_solver = DirectSolver() prob.model.nonlinear_solver = NewtonSolver() prob.setup() prob.run_model() assert_almost_equal(prob['balance.x'], np.sqrt(2), decimal=7) # Assert that normalization is happening assert_almost_equal(prob.model.balance._scale_factor, 1.0 / np.abs(2)) cpd = prob.check_partials(out_stream=None) for (of, wrt) in cpd['balance']: assert_almost_equal(cpd['balance'][of, wrt]['abs error'], 0.0, decimal=5)
def test_result(self): import numpy as np from numpy.testing import assert_almost_equal from openmdao.api import Problem, Group, IndepVarComp, BalanceComp, \ ExecComp, DirectSolver, NewtonSolver prob = Problem(model=Group()) ivc = IndepVarComp() ivc.add_output(name='M', val=0.0, units='deg', desc='Mean anomaly') ivc.add_output(name='ecc', val=0.0, units=None, desc='orbit eccentricity') bal = BalanceComp() bal.add_balance(name='E', val=0.0, units='rad', eq_units='rad', rhs_name='M') # Override the guess_nonlinear method, always initialize E to the value of M def guess_func(inputs, outputs, residuals): outputs['E'] = inputs['M'] bal.guess_nonlinear = guess_func # ExecComp used to compute the LHS of Kepler's equation. lhs_comp = ExecComp('lhs=E - ecc * sin(E)', lhs={'value': 0.0, 'units': 'rad'}, E={'value': 0.0, 'units': 'rad'}, ecc={'value': 0.0}) prob.model.add_subsystem(name='ivc', subsys=ivc, promotes_outputs=['M', 'ecc']) prob.model.add_subsystem(name='balance', subsys=bal, promotes_inputs=['M'], promotes_outputs=['E']) prob.model.add_subsystem(name='lhs_comp', subsys=lhs_comp, promotes_inputs=['E', 'ecc']) # Explicit connections prob.model.connect('lhs_comp.lhs', 'balance.lhs:E') # Setup solvers prob.model.linear_solver = DirectSolver() prob.model.nonlinear_solver = NewtonSolver() prob.model.nonlinear_solver.options['maxiter'] = 100 prob.model.nonlinear_solver.options['iprint'] = 0 prob.setup() prob['M'] = 85.0 prob['ecc'] = 0.6 prob.run_model() assert_almost_equal(np.degrees(prob['E']), 115.9, decimal=1) print('E (deg) = ', np.degrees(prob['E'][0]))
def compute_drag_polar(Mach, alphas, surfaces, trimmed=False): if isinstance(surfaces, dict): surfaces = [surfaces,] # Create the OpenMDAO problem prob = Problem() # Create an independent variable component that will supply the flow # conditions to the problem. indep_var_comp = IndepVarComp() indep_var_comp.add_output('v', val=248.136, units='m/s') indep_var_comp.add_output('alpha', val=0., units = 'deg') indep_var_comp.add_output('M', val=Mach) indep_var_comp.add_output('re', val=1.e6, units='1/m') indep_var_comp.add_output('rho', val=0.38, units='kg/m**3') indep_var_comp.add_output('cg', val=np.zeros((3)), units='m') # Add this IndepVarComp to the problem model prob.model.add_subsystem('prob_vars', indep_var_comp, promotes=['*']) for surface in surfaces: name = surface['name'] # Create and add a group that handles the geometry for the # aerodynamic lifting surface geom_group = Geometry(surface=surface) prob.model.add_subsystem(name, geom_group) # Connect the mesh from the geometry component to the analysis point prob.model.connect(name + '.mesh', 'aero.' + name + '.def_mesh') # Perform the connections with the modified names within the # 'aero_states' group. prob.model.connect(name + '.mesh', 'aero.aero_states.' + name + '_def_mesh') # Create the aero point group, which contains the actual aerodynamic # analyses point_name = 'aero' aero_group = AeroPoint(surfaces=surfaces) prob.model.add_subsystem(point_name, aero_group, promotes_inputs=['v', 'alpha', 'M', 're', 'rho', 'cg']) # For trimmed polar, setup balance component if trimmed == True: bal = BalanceComp() bal.add_balance(name='tail_rotation', rhs_val = 0., units = 'deg') prob.model.add_subsystem('balance', bal, promotes_outputs = ['tail_rotation']) prob.model.connect('aero.CM', 'balance.lhs:tail_rotation', src_indices = [1]) prob.model.connect('tail_rotation', 'tail.twist_cp', src_indices = np.zeros((1,5), dtype = int)) # Use Newton Solver # prob.model.nonlinear_solver = NewtonSolver() # prob.model.nonlinear_solver.options['solve_subsystems'] = True # Use Broyden Solver prob.model.nonlinear_solver = BroydenSolver() prob.model.nonlinear_solver.options['state_vars'] = ['tail_rotation'] # prob.model.nonlinear_solver.linesearch = ArmijoGoldsteinLS() prob.model.nonlinear_solver.options['iprint'] = 2 prob.model.nonlinear_solver.options['maxiter'] = 20 prob.model.linear_solver = DirectSolver() prob.setup() #prob['tail_rotation'] = -0.75 prob.run_model() #prob.check_partials(compact_print = True) #prob.model.list_outputs(prom_name = True) prob.model.list_outputs(residuals = True) CLs = [] CDs = [] CMs = [] for a in alphas: prob['alpha'] = a prob.run_model() CLs.append(prob['aero.CL'][0]) CDs.append(prob['aero.CD'][0]) CMs.append(prob['aero.CM'][1]) # Take only the longitudinal CM #print(a, prob['aero.CL'], prob['aero.CD'], prob['aero.CM'][1]) # Plot CL vs alpha and drag polar fig,axes = plt.subplots(nrows=3) axes[0].plot(alphas, CLs) axes[1].plot(alphas, CMs) axes[2].plot(CLs, CDs) fig.savefig('drag_polar.pdf') #plt.show() return CLs, CDs, CMs
def test_scalar_guess_func_using_outputs(self): model = Group() ind = IndepVarComp() ind.add_output('a', 1) ind.add_output('b', -4) ind.add_output('c', 3) lhs = ExecComp('lhs=-(a*x**2+b*x)') bal = BalanceComp(name='x', rhs_name='c') model.add_subsystem('ind_comp', ind, promotes_outputs=['a', 'b', 'c']) model.add_subsystem('lhs_comp', lhs, promotes_inputs=['a', 'b', 'x']) model.add_subsystem('bal_comp', bal, promotes_inputs=['c'], promotes_outputs=['x']) model.connect('lhs_comp.lhs', 'bal_comp.lhs:x') model.linear_solver = DirectSolver() model.nonlinear_solver = NewtonSolver(maxiter=100, iprint=0) # first verify behavior of the balance comp without the guess function # at initial conditions x=5, x=0 and x=-1 prob = Problem(model) prob.setup() # default solution with initial value of 5 is x=3. prob['x'] = 5 prob.run_model() assert_almost_equal(prob['x'], 3.0, decimal=7) # default solution with initial value of 0 is x=1. prob['x'] = 0 prob.run_model() assert_almost_equal(prob['x'], 1.0, decimal=7) # default solution with initial value of -1 is x=1. prob['x'] = -1 prob.run_model() assert_almost_equal(prob['x'], 1.0, decimal=7) # now use a guess function that steers us to the x=3 solution only # if the initial value of x is less than zero def guess_function(inputs, outputs, residuals): if outputs['x'] < 0: outputs['x'] = 3. bal.options['guess_func'] = guess_function # solution with initial value of 5 is still x=3. prob['x'] = 5 prob.run_model() assert_almost_equal(prob['x'], 3.0, decimal=7) # solution with initial value of 0 is still x=1. prob['x'] = 0 prob.run_model() assert_almost_equal(prob['x'], 1.0, decimal=7) # solution with initial value of -1 is now x=3. prob['x'] = -1 prob.run_model() assert_almost_equal(prob['x'], 3.0, decimal=7)