Example #1
0
class PlaneODE2D(Group):
    ode_options = ODEOptions()

    ode_options.declare_time(units='s')

    # dynamic trajectories
    for i in range(n_traj):
        ode_options.declare_state(
            name='p%dx' % i,
            rate_source='p%d.x_dot' % i,
            targets=['p%d.x' % i,
                     'pairwise.x%d' % i,
                     'space%d.x' % i],
            units='m')
        ode_options.declare_state(
            name='p%dy' % i,
            rate_source='p%d.y_dot' % i,
            targets=['p%d.y' % i,
                     'pairwise.y%d' % i,
                     'space%d.y' % i],
            units='m')
        # ode_options.declare_state(name='p%dmass' % i, rate_source='p%d.mass_dot' % i,
        #                           targets=['p%d.mass' % i], units='kg')
        # ode_options.declare_state(name='p%dimpulse' % i, rate_source='p%d.impulse_dot' % i,
        #                            targets=['t_imp.a%d' % i])

        ode_options.declare_parameter(name='speed%d' % i,
                                      targets='p%d.speed' % i,
                                      dynamic=False)
        ode_options.declare_parameter(name='heading%d' % i,
                                      targets='p%d.heading' % i,
                                      dynamic=False)
        ode_options.declare_parameter(name='isp%d' % i,
                                      targets='p%d.isp' % i,
                                      dynamic=False)

    def initialize(self):
        self.options.declare('num_nodes', types=int)
        self.options.declare('r_space', types=float, default=r_space)
        self.options.declare('ignored_pairs', types=list, default=[])

    def setup(self):
        nn = self.options['num_nodes']
        r_space = self.options['r_space']
        pairs = self.options['ignored_pairs']
        self.linear_solver = DirectSolver()
        self.add_subsystem('t_imp', SumComp(num_nodes=nn, num_arrays=n_traj))

        for i in range(n_traj):
            self.add_subsystem(name='p%d' % i,
                               subsys=PlanePath2D(num_nodes=nn))

            self.add_subsystem(name='space%d' % i,
                               subsys=Space(num_nodes=nn, r_space=r_space))

        self.add_subsystem(name='pairwise',
                           subsys=Pairwise(n_traj=n_traj,
                                           ignored_pairs=pairs,
                                           num_nodes=nn))
Example #2
0
class TankAloneODE(Group):
    """
    Defines the ODE for the fuel circulation problem.
    Here we define the states and parameters (controls) for the problem.

    m : mass of the fuel in the tank
    T : temperature of the fuel in the tank
    energy : energy required to pump the fuel in the system
    """

    ode_options = ODEOptions()

    ode_options.declare_time(units='s')

    ode_options.declare_state('m', units='kg', rate_source='m_dot', targets=['m'])
    ode_options.declare_state('T', units='K', rate_source='T_dot', targets=['T'])
    ode_options.declare_state('energy', units='J', rate_source='power')

    ode_options.declare_parameter('m_flow', targets=['m_flow'], units='kg/s')
    ode_options.declare_parameter('m_burn', targets=['m_burn'], units='kg/s')
    ode_options.declare_parameter('Q_env', targets=['Q_env'], units='W')
    ode_options.declare_parameter('Q_sink', targets=['Q_sink'], units='W')
    ode_options.declare_parameter('Q_out', targets=['Q_out'], units='W')

    def initialize(self):
        self.options.declare('num_nodes', types=int)

    def setup(self):
        nn = self.options['num_nodes']

        self.add_subsystem(name='cv',
                           subsys=CvComp(num_nodes=nn),
                           promotes_inputs=['T'],
                           promotes_outputs=['Cv'])

        self.add_subsystem(name='tank',
                           subsys=TankAloneComp(num_nodes=nn),
                           promotes_inputs=['m', 'm_flow', 'm_burn', 'T', 'Q_env', 'Q_sink', 'Q_out', 'Cv'],
                           promotes_outputs=['m_dot', 'T_dot', 'm_recirculated', 'T_o'])

        self.add_subsystem(name='power',
                           subsys=PowerComp(num_nodes=nn),
                           promotes=['m_flow', 'power'])

        # Set solvers
        self.nonlinear_solver = NonlinearBlockGS()
        self.linear_solver = DirectSolver(assemble_jac=True)
        self.options['assembled_jac_type'] = 'csc'
class MyODE(Group):
    ode_options = ODEOptions()
    ode_options.declare_time(units='s', targets=['comp.time'])
    ode_options.declare_state(name='F', rate_source='comp.y')
    ode_options.declare_parameter(name='alpha',
                                  shape=(n_traj, 2),
                                  targets='comp.alpha',
                                  dynamic=False)

    def initialize(self):
        self.options.declare('num_nodes', types=int)
        self.options.declare('n_traj', default=2, types=int)

    def setup(self):
        nn = self.options['num_nodes']
        n_traj = self.options['n_traj']

        self.add_subsystem(name='comp',
                           subsys=MyComp(num_nodes=nn, n_traj=n_traj))
class _CannonballODE(FlightPathEOM2D):

    ode_options = ODEOptions()

    ode_options.declare_time(units='s')

    ode_options.declare_state(name='r', rate_source='r_dot', units='m')
    ode_options.declare_state(name='h', rate_source='h_dot', units='m')
    ode_options.declare_state(name='gam',
                              rate_source='gam_dot',
                              targets='gam',
                              units='rad')
    ode_options.declare_state(name='v',
                              rate_source='v_dot',
                              targets='v',
                              units='m/s')

    def __init__(self, **kwargs):
        super(_CannonballODE, self).__init__(**kwargs)
class MinTimeClimbODE(Group):

    ode_options = ODEOptions()

    ode_options.declare_time(units='s')

    ode_options.declare_state('r',
                              units='km',
                              rate_source='flight_dynamics.r_dot')
    ode_options.declare_state('h',
                              units='m',
                              rate_source='flight_dynamics.h_dot',
                              targets=['h'])
    ode_options.declare_state('v',
                              units='m/s',
                              rate_source='flight_dynamics.v_dot',
                              targets=['v'])
    ode_options.declare_state('gam',
                              units='rad',
                              rate_source='flight_dynamics.gam_dot',
                              targets=['gam'])
    ode_options.declare_state('m',
                              units='kg',
                              rate_source='prop.m_dot',
                              targets=['m'])

    ode_options.declare_parameter('alpha', targets=['alpha'], units='rad')

    ode_options.declare_parameter('throttle', targets=['throttle'], units=None)

    def initialize(self):
        self.options.declare('num_nodes', types=int)

    def setup(self):
        nn = self.options['num_nodes']

        self.add_subsystem(name='atmos',
                           subsys=StandardAtmosphereGroup(num_nodes=nn),
                           promotes_inputs=['h'])

        self.add_subsystem(
            name='aero',
            subsys=AeroGroup(num_nodes=nn),
            promotes_inputs=['v', 'alpha'],
        )

        self.connect('atmos.sos', 'aero.sos')
        self.connect('atmos.rho', 'aero.rho')

        self.add_subsystem(name='prop',
                           subsys=PropGroup(num_nodes=nn),
                           promotes_inputs=['h', 'throttle'])

        self.connect('aero.mach', 'prop.mach')

        self.add_subsystem(name='flight_dynamics',
                           subsys=FlightPathEOM2D(num_nodes=nn),
                           promotes_inputs=['m', 'v', 'gam', 'alpha'])

        self.connect('aero.f_drag', 'flight_dynamics.D')
        self.connect('aero.f_lift', 'flight_dynamics.L')
        self.connect('prop.thrust', 'flight_dynamics.T')
class SimpleHeatODE(Group):
    """
    Defines the ODE for the fuel circulation problem.
    Here we define the states and parameters (controls) for the problem.

    m : mass of the fuel in the tank
    T : temperature of the fuel in the tank
    energy : energy required to pump the fuel in the system
    """

    ode_options = ODEOptions()

    ode_options.declare_time(units='s')

    ode_options.declare_state('m', units='kg', rate_source='m_dot', targets=['m'])
    ode_options.declare_state('T', units='K', rate_source='T_dot', targets=['T'])
    ode_options.declare_state('energy', units='J', rate_source='power')

    ode_options.declare_parameter('m_flow', targets=['m_flow'], units='kg/s')
    ode_options.declare_parameter('m_burn', targets=['m_burn'], units='kg/s')

    def initialize(self):
        self.options.declare('num_nodes', types=int)
        self.options.declare('q_tank', types=float)
        self.options.declare('q_hx1', types=float)
        self.options.declare('q_hx2', types=float)

    def setup(self):
        nn = self.options['num_nodes']
        q_tank = self.options['q_tank']
        q_hx1 = self.options['q_hx1']
        q_hx2 = self.options['q_hx2']

        self.add_subsystem(name='tank',
                           subsys=TankComp(num_nodes=nn, q=q_tank),
                           promotes=['m', 'm_flow', 'm_dot', 'T', 'T_dot'])

        self.add_subsystem(name='heat_exchanger_pre',
                           subsys=HeatExchangerComp(num_nodes=nn, q=q_hx1),
                           promotes=[])

        self.add_subsystem(name='fuel_burner',
                           subsys=FuelBurnerComp(num_nodes=nn),
                           promotes=['m_burn'])

        self.add_subsystem(name='heat_exchanger_post',
                           subsys=HeatExchangerComp(num_nodes=nn, q=q_hx2),
                           promotes=[])

        self.add_subsystem(name='power',
                           subsys=PowerComp(num_nodes=nn),
                           promotes=['m_flow', 'power'])

        # Tank to HX1
        self.connect('tank.T_out', 'heat_exchanger_pre.T_in')
        self.connect('tank.m_out', 'heat_exchanger_pre.m_in')

        # HX1 to HX2
        self.connect('heat_exchanger_pre.T_out', 'heat_exchanger_post.T_in')

        # HX1 to burner
        self.connect('tank.m_out', 'fuel_burner.m_in')

        # Burner to HX2
        self.connect('fuel_burner.m_recirculated', 'heat_exchanger_post.m_in')

        # HX2 to tank
        self.connect('heat_exchanger_post.T_out', 'tank.T_in')
        self.connect('fuel_burner.m_recirculated', 'tank.m_in')

        # Set solvers
        self.nonlinear_solver = NonlinearBlockGS()
        self.linear_solver = DirectSolver(assembled_jac=True)
class ThermalMissionODE(Group):

    ode_options = ODEOptions()

    ode_options.declare_time(units='s')

    # Mission and aero
    ode_options.declare_state('r',
                              units='m',
                              rate_source='flight_dynamics.r_dot')
    ode_options.declare_state('h',
                              units='m',
                              rate_source='flight_dynamics.h_dot',
                              targets=['h'])
    ode_options.declare_state('v',
                              units='m/s',
                              rate_source='flight_dynamics.v_dot',
                              targets=['v'])
    ode_options.declare_state('gam',
                              units='rad',
                              rate_source='flight_dynamics.gam_dot',
                              targets=['gam'])
    ode_options.declare_state('m',
                              units='kg',
                              rate_source='m_dot',
                              targets=['m'])

    ode_options.declare_parameter('alpha', targets=['alpha'], units='rad')
    ode_options.declare_parameter('S', targets=['S'], units='m**2')
    ode_options.declare_parameter('throttle', targets=['throttle'], units=None)
    ode_options.declare_parameter('W0', targets=['W0'], units='kg')

    # Thermal
    ode_options.declare_state('T',
                              units='K',
                              rate_source='T_dot',
                              targets=['T'])
    ode_options.declare_state('energy', units='J', rate_source='power')

    ode_options.declare_parameter('m_recirculated',
                                  targets=['m_recirculated'],
                                  units='kg/s')
    ode_options.declare_parameter('Q_env', targets=['Q_env'], units='W')
    ode_options.declare_parameter('Q_sink', targets=['Q_sink'], units='W')
    ode_options.declare_parameter('Q_out', targets=['Q_out'], units='W')

    def initialize(self):
        self.options.declare('num_nodes', types=int)
        self.options.declare('engine_heat_coeff', types=float)
        self.options.declare('pump_heat_coeff', types=float)

    def setup(self):
        nn = self.options['num_nodes']
        engine_heat_coeff = self.options['engine_heat_coeff']
        pump_heat_coeff = self.options['pump_heat_coeff']

        # Aero and mission
        self.add_subsystem(name='atmos',
                           subsys=StandardAtmosphereGroup(num_nodes=nn),
                           promotes_inputs=['h'])

        # self.add_subsystem(name='aero',
        #                    subsys=AeroGroup(num_nodes=nn),
        #                    promotes_inputs=['v', 'alpha', 'S'])

        self.add_subsystem(name='aero',
                           subsys=AeroSMTGroup(num_nodes=nn),
                           promotes_inputs=['v', 'alpha', 'S', 'h'])

        self.connect('atmos.sos', 'aero.sos')
        self.connect('atmos.rho', 'aero.rho')

        self.add_subsystem(name='prop',
                           subsys=PropGroup(num_nodes=nn),
                           promotes_inputs=['h', 'throttle'],
                           promotes_outputs=['m_dot'])

        self.connect('aero.mach', 'prop.mach')

        self.add_subsystem(name='flight_dynamics',
                           subsys=FlightPathEOM2D(num_nodes=nn),
                           promotes_inputs=['m', 'v', 'gam', 'alpha'])

        self.connect('aero.f_drag', 'flight_dynamics.D')
        self.connect('aero.f_lift', 'flight_dynamics.L')
        self.connect('prop.thrust', 'flight_dynamics.T')

        # Thermal
        self.add_subsystem(
            'm_burn_comp',
            ExecComp('m_burn = - m_dot',
                     m_burn=np.zeros(nn),
                     m_dot=np.zeros(nn)),
            promotes=['*'],
        )

        self.add_subsystem(
            'm_fuel_comp',
            ExecComp('m_fuel = m - W0',
                     m_fuel=np.zeros(nn),
                     m=np.zeros(nn),
                     W0=np.zeros(nn)),
            promotes=['*'],
        )

        self.add_subsystem(
            'm_flow_comp',
            ExecComp('m_flow = m_burn + m_recirculated',
                     m_flow=np.zeros(nn),
                     m_burn=np.zeros(nn),
                     m_recirculated=np.zeros(nn)),
            promotes=['*'],
        )

        self.add_subsystem(name='pump_heating_comp',
                           subsys=PumpHeatingComp(num_nodes=nn,
                                                  heat_coeff=pump_heat_coeff),
                           promotes_inputs=['m_flow'],
                           promotes_outputs=['Q_pump'])

        self.add_subsystem(name='engine_heating_comp',
                           subsys=EngineHeatingComp(
                               num_nodes=nn, heat_coeff=engine_heat_coeff),
                           promotes_inputs=['throttle'],
                           promotes_outputs=['Q_engine'])

        self.add_subsystem(
            'Q_env_tot_comp',
            ExecComp('Q_env_tot = Q_env + Q_pump + Q_engine',
                     Q_env_tot=np.zeros(nn),
                     Q_env=np.zeros(nn),
                     Q_pump=np.zeros(nn),
                     Q_engine=np.zeros(nn)),
            promotes=['*'],
        )

        self.add_subsystem(name='cv',
                           subsys=CvComp(num_nodes=nn),
                           promotes_inputs=['T'],
                           promotes_outputs=['Cv'])

        self.add_subsystem(name='tank',
                           subsys=TankMissionComp(num_nodes=nn),
                           promotes_inputs=[
                               'm_fuel', 'm_flow', 'm_burn', 'T', 'Q_env_tot',
                               'Q_sink', 'Q_out', 'Cv'
                           ],
                           promotes_outputs=['T_dot', 'T_o'])

        self.add_subsystem(name='power',
                           subsys=PowerComp(num_nodes=nn),
                           promotes=['m_flow', 'power'])

        # Set solvers
        self.linear_solver = DirectSolver(assemble_jac=True)
        self.options['assembled_jac_type'] = 'csc'
Example #8
0
class PlaneODE2D(Group):
    ode_options = ODEOptions()

    ode_options.declare_time(
        units='s',
        targets=['keepout%d.time' % i for i in range(n_traj)] +
        ['schedule%d.time' % i for i in range(n_traj)])

    targets = {}
    for i in range(n_traj):
        targets[i] = {
            'x': ['keepout%d.x' % i, 'schedule%d.x' % i],
            'y': ['keepout%d.y' % i, 'schedule%d.y' % i]
        }

    for i, j in combinations([i for i in range(n_traj)], 2):
        targets[i]['x'].append('distance_%d_%d.x1' % (i, j))
        targets[i]['y'].append('distance_%d_%d.y1' % (i, j))

        targets[j]['x'].append('distance_%d_%d.x2' % (i, j))
        targets[j]['y'].append('distance_%d_%d.y2' % (i, j))

    # dynamic trajectories
    for i in range(n_traj):
        ode_options.declare_state(name='x%d' % i,
                                  rate_source='flight_path%d.x_dot' % i,
                                  targets=targets[i]['x'],
                                  units='m')
        ode_options.declare_state(name='y%d' % i,
                                  rate_source='flight_path%d.y_dot' % i,
                                  targets=targets[i]['y'],
                                  units='m')
        #ode_options.declare_state(name='L%d' % i, rate_source='flight_path%d.L_dot' % i, units='m')
        ode_options.declare_parameter(name='vx%d' % i,
                                      targets='flight_path%d.vx' % i,
                                      units='m/s')
        ode_options.declare_parameter(name='vy%d' % i,
                                      targets='flight_path%d.vy' % i,
                                      units='m/s')

        ode_options.declare_parameter(name='sx%d' % i,
                                      targets='schedule%d.x_start' % i,
                                      units='m')
        ode_options.declare_parameter(name='sy%d' % i,
                                      targets='schedule%d.y_start' % i,
                                      units='m')
        ode_options.declare_parameter(name='ex%d' % i,
                                      targets='schedule%d.x_end' % i,
                                      units='m')
        ode_options.declare_parameter(name='ey%d' % i,
                                      targets='schedule%d.y_end' % i,
                                      units='m')

        ode_options.declare_parameter(name='ts%d' % i,
                                      targets='schedule%d.t_departure' % i,
                                      units='s')
        ode_options.declare_parameter(name='te%d' % i,
                                      targets='schedule%d.t_arrival' % i,
                                      units='s')

    def initialize(self):
        self.options.declare('num_nodes', types=int)

    def setup(self):
        nn = self.options['num_nodes']
        self.add_subsystem('vtotals', subsys=VSum(n_traj=n_traj))
        for i in range(n_traj):
            self.add_subsystem(name='flight_path%d' % i,
                               subsys=FlightPathEOM2D(num_nodes=nn))
            self.connect('flight_path%d.vt' % i, 'vtotals.v%d' % i)

            self.add_subsystem(name='schedule%d' % i,
                               subsys=Schedule(num_nodes=nn))

            self.add_subsystem('keepout%d' % i,
                               subsys=KeepOut(num_nodes=nn,
                                              x_loc=x_loc,
                                              y_loc=y_loc,
                                              ts=ks_start))

        traj = [i for i in range(n_traj)]
        for i, j in combinations(traj, 2):
            self.add_subsystem('distance_%d_%d' % (i, j),
                               subsys=Distance(num_nodes=nn))