def __init__(self, iotype, client, rpath): ProxyMixin.__init__(self, client, rpath) default = float(self._valstr) desc = client.get(rpath+'.description') as_units = client.get(rpath+'.units') if as_units: om_units = get_translation(as_units) else: om_units = None if client.get(rpath+'.hasUpperBound') == 'true': high = float(client.get(rpath+'.upperBound')) else: high = None if client.get(rpath+'.hasLowerBound') == 'true': low = float(client.get(rpath+'.lowerBound')) else: low = None Float.__init__(self, default_value=default, iotype=iotype, desc=desc, low=low, high=high, units=om_units)
def test_large_dataflow_nested_assys(self): self.top = set_as_top(Assembly()) exp1 = ['y1 = 2.0*x1**2', 'y2 = 3.0*x1'] deriv1 = ['dy1_dx1 = 4.0*x1', 'dy2_dx1 = 3.0'] exp2 = ['y1 = 0.5*x1'] deriv2 = ['dy1_dx1 = 0.5'] exp3 = ['y1 = 3.5*x1'] deriv3 = ['dy1_dx1 = 3.5'] exp4 = ['y1 = x1 + 2.0*x2', 'y2 = 3.0*x1', 'y3 = x1*x2'] deriv4 = [ 'dy1_dx1 = 1.0', 'dy1_dx2 = 2.0', 'dy2_dx1 = 3.0', 'dy2_dx2 = 0.0', 'dy3_dx1 = x2', 'dy3_dx2 = x1' ] exp5 = ['y1 = x1 + 3.0*x2 + 2.0*x3'] deriv5 = ['dy1_dx1 = 1.0', 'dy1_dx2 = 3.0', 'dy1_dx3 = 2.0'] self.top.add('nest1', Assembly()) self.top.add('comp1', ExecCompWithDerivatives(exp1, deriv1)) self.top.nest1.add('comp2', ExecCompWithDerivatives(exp2, deriv2)) self.top.nest1.add('comp3', ExecCompWithDerivatives(exp3, deriv3)) self.top.nest1.add('comp4', ExecCompWithDerivatives(exp4, deriv4)) self.top.add('comp5', ExecCompWithDerivatives(exp5, deriv5)) self.top.add('driver', Driv()) self.top.driver.workflow.add(['comp1', 'nest1', 'comp5']) self.top.nest1.driver.workflow.add(['comp2', 'comp3', 'comp4']) self.top.driver.differentiator = ChainRule() obj = 'comp5.y1' con = 'comp5.y1-nest1.comp3.y1 > 0' self.top.driver.add_parameter('comp1.x1', low=-50., high=50., fd_step=.0001) self.top.driver.add_objective(obj) self.top.driver.add_constraint(con) self.top.nest1.add('real_c2_x1', Float(iotype='in', desc='I am really here')) self.top.nest1.add('real_c3_x1', Float(iotype='in', desc='I am really here')) self.top.nest1.add('real_c4_y1', Float(iotype='out', desc='I am really here')) self.top.nest1.add('real_c4_y2', Float(iotype='out', desc='I am really here')) self.top.nest1.add('real_c4_y3', Float(iotype='out', desc='I am really here')) #self.top.connect('comp1.y1', 'nest1.comp2.x1') self.top.connect('comp1.y1', 'nest1.real_c2_x1') self.top.connect('comp1.y2', 'nest1.real_c3_x1') self.top.nest1.connect('real_c2_x1', 'comp2.x1') self.top.nest1.connect('real_c3_x1', 'comp3.x1') self.top.nest1.connect('comp2.y1', 'comp4.x1') self.top.nest1.connect('comp3.y1', 'comp4.x2') self.top.nest1.connect('comp4.y1', 'real_c4_y1') self.top.nest1.connect('comp4.y2', 'real_c4_y2') self.top.nest1.connect('comp4.y3', 'real_c4_y3') self.top.connect('nest1.real_c4_y1', 'comp5.x1') self.top.connect('nest1.real_c4_y2', 'comp5.x2') self.top.connect('nest1.real_c4_y3', 'comp5.x3') #self.top.connect('nest1.comp4.y1', 'comp5.x1') #self.top.connect('nest1.comp4.y3', 'comp5.x3') self.top.comp1.x1 = 2.0 self.top.run() self.top.driver.differentiator.calc_gradient() grad = self.top.driver.differentiator.get_gradient(obj) assert_rel_error(self, grad[0], 313.0, .001) grad = self.top.driver.differentiator.get_gradient( 'comp5.y1-nest1.comp3.y1>0') assert_rel_error(self, grad[0], -313.0 + 10.5, .001)
class OffshorePlot(TopfarmComponent): wt_positions = Array( [], unit='m', iotype='in', desc='Array of wind turbines attached to particular positions') baseline = Array( [], unit='m', iotype='in', desc='Array of wind turbines attached to particular positions') borders = Array(iotype='in', desc='The polygon defining the borders ndarray([n_bor,2])', unit='m') depth = Array(iotype='in', desc='An array of depth ndarray([n_d, 2])', unit='m') foundations = Array(iotype='in', desc='The foundation length ofeach wind turbine') #wt_dist = Array(iotype='in', desc="""The distance between each turbines ndarray([n_wt, n_wt]).""", unit='m') spiral_param = Float(5.0, iotype='in', desc='spiral parameter') png_name = Str('wind_farm', iotype='in', desc='The base of the png name used to save the fig') result_file = Str('wind_farm', iotype='in', desc='The base result name used to save the fig') distribution = Str('spiral', iotype='in', desc='The type of distribution to plot') elnet_layout = Dict(iotype='in') inc = 0 fs = 15 #Font size def __init__(self, add_inputs, title='', **kwargs): super(OffshorePlot, self).__init__(**kwargs) self.fig = plt.figure(num=None, facecolor='w', edgecolor='k') #figsize=(13, 8), dpi=1000 self.shape_plot = self.fig.add_subplot(121) self.objf_plot = self.fig.add_subplot(122) self.targname = add_inputs self.title = title # Adding automatically the inputs for i in add_inputs: self.add(i, Float(0.0, iotype='in')) #sns.set(style="darkgrid") #self.pal = sns.dark_palette("skyblue", as_cmap=True) plt.rc('lines', linewidth=1) plt.ion() self.force_execute = True if not pa('fig').exists(): pa('fig').mkdir() def execute(self): plt.ion() if self.inc == 0: try: pa(self.result_file + '.results').remove() except: pass self.iterations = [self.inc] self.targvalue = [[getattr(self, i) for i in self.targname]] self.pre_plot() else: self.iterations.append(self.inc) self.targvalue.append([getattr(self, i) for i in self.targname]) #print self.iterations,self.targvalue #if self.inc % (2*self.wt_positions.shape[0]) == 0: #self.refresh() #plt.show() self.save_plot('fig/' + self.png_name + 'layout%d.png' % (self.inc)) self.inc += 1 def pre_plot(self): plt.ion() #plt.show() ### Plot the water depth N = 100 self.X, self.Y = plt.meshgrid( plt.linspace(self.depth[:, 0].min(), self.depth[:, 0].max(), N), plt.linspace(self.depth[:, 1].min(), self.depth[:, 1].max(), N)) self.Z = plt.griddata(self.depth[:, 0], self.depth[:, 1], self.depth[:, 2], self.X, self.Y, interp='linear') Zin = points_in_poly(self.X, self.Y, self.borders) self.Z.mask = Zin.__neg__() #Z.mask = False #Z.data[Zin.__neg__()] = -20.0 display(plt.gcf()) # def refresh(self): self.shape_plot.clear() self.shape_plot.contourf(self.X, self.Y, self.Z, 10, vmax=self.depth[:, 2].max()) #, cmap=self.pal self.shape_plot.set_aspect('equal') self.shape_plot.autoscale(tight=True) Plot = lambda b, *args, **kwargs: self.shape_plot.plot( b[:, 0], b[:, 1], *args, **kwargs) if self.distribution == 'spiral': spiral = lambda t_, a_, x_: [ a_ * t_**(1. / x_) * np.cos(t_), a_ * t_** (1. / x_) * np.sin(t_) ] spirals = lambda ts_, a_, x_: np.array( [spiral(t_, a_, x_) for t_ in ts_]) for P in self.baseline: Plot(P + spirals(plt.linspace(0., 10 * np.pi, 1000), self.spiral_param, 1.), 'g-', linewidth=0.1) self.shape_plot.plot(self.borders[:, 0], self.borders[:, 1], 'k-') self.posi = self.shape_plot.plot(self.wt_positions[:, 0], self.wt_positions[:, 1], 'ro') self.plotel = self.shape_plot.plot( np.array([ self.baseline[[i, j], 0] for i, j in self.elnet_layout.keys() ]).T, np.array([ self.baseline[[i, j], 1] for i, j in self.elnet_layout.keys() ]).T, 'y--', linewidth=1) #print self.plotel self.objf_plot.clear() targarr = np.array(self.targvalue) self.posb = [] for i in range(targarr.shape[1]): self.posb.append( self.objf_plot.plot(self.iterations, self.targvalue[0][i], '.', label=self.targname[i])) print 'posb', self.posb self.legend = self.objf_plot.legend(loc=3, bbox_to_anchor=(1.1, 0.0)) plt.title('Foundation = %8.2f' % (self.foundation_length)) plt.draw() def save_plot(self, filename): plt.ion() targarr = np.array(self.targvalue) self.posi[0].set_xdata(self.wt_positions[:, 0]) self.posi[0].set_ydata(self.wt_positions[:, 1]) while len(self.plotel) > 0: self.plotel.pop(0).remove() self.plotel = self.shape_plot.plot( np.array([ self.wt_positions[[i, j], 0] for i, j in self.elnet_layout.keys() ]).T, np.array([ self.wt_positions[[i, j], 1] for i, j in self.elnet_layout.keys() ]).T, 'y-', linewidth=1) for i in range(len(self.posb)): self.posb[i][0].set_xdata(self.iterations) self.posb[i][0].set_ydata(targarr[:, i]) self.legend.texts[i].set_text('%s = %8.2f' % (self.targname[i], targarr[-1, i])) self.objf_plot.set_xlim([0, self.iterations[-1]]) self.objf_plot.set_ylim([0.5, 1.2]) if not self.title == '': plt.title('%s = %8.2f' % (self.title, getattr(self, self.title))) plt.draw() #print self.iterations[-1] , ': ' + ', '.join(['%s=%6.2f'%(self.targname[i], targarr[-1,i]) for i in range(len(self.targname))]) with open(self.result_file + '.results', 'a') as f: f.write('%d:' % (self.inc) + ', '.join([ '%s=%6.2f' % (self.targname[i], targarr[-1, i]) for i in range(len(self.targname)) ]) + '\n') #plt.show() #plt.savefig(filename) display(plt.gcf()) #plt.show() clear_output(wait=True)
def test_subassy_units(self): self.top = set_as_top(Assembly()) self.top.add('nest1', Assembly()) self.top.add('comp1', CompFoot()) self.top.nest1.add('comp2', CompInch()) self.top.add('comp3', CompFoot()) self.top.nest1.add( 'nestx', Float(iotype='in', units='inch', desc='Legit connection')) self.top.nest1.add( 'nesty', Float(iotype='out', units='inch', desc='Legit connection')) #self.top.connect('comp1.y', 'nest1.comp2.x') self.top.connect('1.0*comp1.y', 'nest1.nestx') self.top.nest1.connect('nestx', 'comp2.x') #self.top.connect('nest1.comp2.y', 'comp3.x') self.top.nest1.connect('comp2.y', 'nesty') self.top.connect('1.0*nest1.nesty', 'comp3.x') self.top.add('driver', Driv()) self.top.driver.workflow.add(['comp1', 'nest1', 'comp3']) self.top.nest1.driver.workflow.add(['comp2']) self.top.driver.differentiator = ChainRule() obj = 'comp3.y' con = 'nest1.nesty>0' self.top.driver.add_parameter('comp1.x', low=-50., high=50., fd_step=.0001) self.top.driver.add_objective(obj) self.top.driver.add_constraint(con) self.top.comp1.x = 1.0 self.top.run() self.top.driver.differentiator.calc_gradient() grad = self.top.driver.differentiator.get_gradient(obj) assert_rel_error(self, grad[0], 8.0, .001) grad = self.top.driver.differentiator.get_gradient(con) assert_rel_error(self, grad[0], -48.0, .001) # Testing conversion at this boundary (ft instead of inch) self.top.nest1.add( 'nestx', Float(iotype='in', units='ft', desc='Legit connection')) self.top.nest1.add( 'nesty', Float(iotype='out', units='inch', desc='Legit connection')) self.top.comp1.x = 1.0 self.top.run() self.top.driver.differentiator.calc_gradient() grad = self.top.driver.differentiator.get_gradient(obj) assert_rel_error(self, grad[0], 8.0, .001) grad = self.top.driver.differentiator.get_gradient(con) assert_rel_error(self, grad[0], -48.0, .001)
class HyperloopPod(Assembly): #Design Variables Mach_pod_max = Float(1.0, iotype="in", desc="travel Mach of the pod") Mach_c1_in = Float(.6, iotype="in", desc="Mach number at entrance to the first compressor at design conditions") Mach_bypass = Float(.95, iotype="in", desc="Mach in the air passing around the pod") c1_PR_des = Float(12.47, iotype="in", desc="pressure ratio of first compressor at design conditions") Ps_tube = Float(99, iotype="in", desc="static pressure in the tube", units="Pa", low=0) #Parameters solar_heating_factor = Float(.7, iotype="in", desc="Fractional amount of solar radiation to consider in tube temperature calculations", low=0, high=1) tube_length = Float(563270, units = 'm', iotype='in', desc='Length of entire Hyperloop') pwr_marg = Float(.3, iotype="in", desc="fractional extra energy requirement") hub_to_tip = Float(.4, iotype="in", desc="hub to tip ratio for the compressor") coef_drag = Float(2, iotype="in", desc="capsule drag coefficient") n_rows = Int(14, iotype="in", desc="number of rows of seats in the pod") length_row = Float(150, iotype="in", units="cm", desc="length of each row of seats") def configure(self): #Add Components compress = self.add('compress', CompressionSystem()) mission = self.add('mission', Mission()) pod = self.add('pod', Pod()) flow_limit = self.add('flow_limit', TubeLimitFlow()) tube_wall_temp = self.add('tube_wall_temp', TubeWallTemp()) #Boundary Input Connections #Hyperloop -> Compress self.connect('Mach_pod_max', 'compress.Mach_pod_max') self.connect('Ps_tube', 'compress.Ps_tube') self.connect('Mach_c1_in','compress.Mach_c1_in') #Design Variable self.connect('c1_PR_des', 'compress.c1_PR_des') #Design Variable #Hyperloop -> Mission self.connect('tube_length', 'mission.tube_length') self.connect('pwr_marg','mission.pwr_marg') #Hyperloop -> Flow Limit self.connect('Mach_pod_max', 'flow_limit.Mach_pod') self.connect('Ps_tube', 'flow_limit.Ps_tube') self.connect('pod.radius_inlet_back_outer', 'flow_limit.radius_inlet') self.connect('Mach_bypass','flow_limit.Mach_bypass') #Hyperloop -> Pod self.connect('Ps_tube', 'pod.Ps_tube') self.connect('hub_to_tip','pod.hub_to_tip') self.connect('coef_drag','pod.coef_drag') self.connect('n_rows','pod.n_rows') self.connect('length_row','pod.length_row') #Hyperloop -> TubeWallTemp self.connect('solar_heating_factor', 'tube_wall_temp.nn_incidence_factor') self.connect('tube_length', 'tube_wall_temp.length_tube') #Inter-component Connections #Compress -> Mission self.connect('compress.speed_max', 'mission.speed_max') self.connect('compress.pwr_req', 'mission.pwr_req') #Compress -> Pod self.connect('compress.area_c1_in', 'pod.area_inlet_out') self.connect('compress.area_inlet_in', 'pod.area_inlet_in') self.connect('compress.rho_air', 'pod.rho_air') self.connect('compress.F_net','pod.F_net') self.connect('compress.speed_max', 'pod.speed_max') #Compress -> TubeWallTemp self.connect('compress.nozzle_Fl_O', 'tube_wall_temp.nozzle_air') self.connect('compress.bearing_Fl_O', 'tube_wall_temp.bearing_air') #Mission -> Pod self.connect('mission.time','pod.time_mission') self.connect('mission.energy', 'pod.energy') #Add Solver solver = self.add('solver',BroydenSolver()) solver.itmax = 50 #max iterations solver.tol = .001 #Add Parameters and Constraints solver.add_parameter('compress.W_in',low=-1e15,high=1e15) solver.add_parameter('compress.c2_PR_des', low=-1e15, high=1e15) solver.add_parameter(['compress.Ts_tube','flow_limit.Ts_tube','tube_wall_temp.temp_boundary'], low=-1e-15, high=1e15) solver.add_parameter(['flow_limit.radius_tube', 'pod.radius_tube_inner'], low=-1e15, high=1e15) solver.add_constraint('.01*(compress.W_in-flow_limit.W_excess) = 0') solver.add_constraint('compress.Ps_bearing_residual=0') solver.add_constraint('tube_wall_temp.ss_temp_residual=0') solver.add_constraint('.01*(pod.area_compressor_bypass-compress.area_c1_out)=0') driver = self.driver driver.workflow.add('solver') #driver.recorders = [CSVCaseRecorder(filename="hyperloop_data.csv")] #record only converged #driver.printvars = ['Mach_bypass', 'Mach_pod_max', 'Mach_c1_in', 'c1_PR_des', 'pod.radius_inlet_back_outer', # 'pod.inlet.radius_back_inner', 'flow_limit.radius_tube', 'compress.W_in', 'compress.c2_PR_des', # 'pod.net_force', 'compress.F_net', 'compress.pwr_req', 'pod.energy', 'mission.time', # 'compress.speed_max', 'tube_wall_temp.temp_boundary'] #Declare Solver Workflow solver.workflow.add(['compress','mission','pod','flow_limit','tube_wall_temp'])
class PdcylComp(ExternalCode): """ OpenMDAO component wrapper for PDCYL. """ icalc = Bool(False, iotype='in', desc='Print switch. Set to True for verbose output.') title = Str("PDCYl Component", iotype='in', desc='Title of the analysis') # Wing geometry # -------------------- wsweep = Float(iotype='in', units='deg', desc='Wing sweep referenced to the leading edge') war = Float(iotype='in', desc='Wing Aspect Ratio') wtaper = Float(iotype='in', desc=' Wing taper ratio') wtcroot = Float(iotype='in', desc=' Wing thickness-to-cord at root') wtctip = Float(iotype='in', desc=' Wing thickness-to-cord at tip') warea = Float(iotype='in', units='ft**2', desc='Wing planform area') # Material properties # -------------------- ps = Float(iotype='in', desc='Plasticity factor') tmgw = Float(iotype='in', units='inch', desc='Min. gage thickness for the wing') effw = Float(iotype='in', desc='Buckling efficiency of the web') effc = Float(iotype='in', desc='Buckling efficiency of the covers') esw = Float(iotype='in', units='psi', desc="Young's Modulus for wing material") fcsw = Float(iotype='in', units='psi', desc='Ult. compressive strength of wing') dsw = Float(iotype='in', units='lb/inch**3', desc=' Density of the wing material') kdew = Float(iotype='in', desc="Knock-down factor for Young's Modulus") kdfw = Float(iotype='in', desc='Knock-down factor for Ultimate strength') # Geometric parameters # -------------------- istama = Enum( [1, 2], iotype='in', desc=' 1 - Position of wing is unknown; 2 - position is known') cs1 = Float( iotype='in', desc= 'Position of structural wing box from leading edge as percent of root chord' ) cs2 = Float( iotype='in', desc= ' Position of structural wing box from trailing edge as percent of root chord' ) uwwg = Float(iotype='in', units='lb/ft**2', desc=' Wing Weight / Wing Area of baseline aircraft ') xwloc1 = Float(iotype='in', desc=' Location of wing as a percentage of body length') # Structural Concept # -------------------- claqr = Float(iotype='in', desc='Ratio of body lift to wing lift') ifuel = Enum( [1, 2], iotype='in', desc= ' 1 - No fuel is stored in the wing; 2 - Fuel is stored in the wing') cwman = Float(iotype='in', desc='Design maneuver load factor') cf = Float(iotype='in', desc="Shanley's const. for frame bending") # Tails # -------------------- itail = Enum( [1, 2], iotype='in', desc= ' 1 - Control surfaces mounted on tail; 2 - Control surfaces mounted on wing' ) uwt = Float( iotype='in', units='lb/ft**2', desc='(Htail Weight + Vtail Weight) / Htail Area of baseline aircraft') clrt = Float(iotype='in', desc=' Location of tail as a percentage of body length') harea = Float(iotype='in', units='ft**2', desc=' Location of tail as a percentage of body length') # Fuselage geometry # -------------------- frn = Float( iotype='in', desc='Fineness ratio of the nose section (length/diameter)') frab = Float( iotype='in', desc='Fineness ratio of the after-body section (length/diameter)') bodl = Float(iotype='in', units='ft', desc='Length of the fuselage ') bdmax = Float(iotype='in', units='ft', desc='Maximum diameter of fuselage') # These vars are listed in the pdcyl code, but they are never read in. Not sure # what that's all about. #vbod = Float(iotype='in', units='ft**3', desc='Fuselage total volume ') #volnose = Float(iotype='in', units='ft**3', desc='Nose Volume') #voltail = Float(iotype='in', units='ft**3', desc='Tail volume ') # Structural Concept # -------------------- ckf = Float(iotype='in', desc='Frame stiffness coefficient') ec = Float(iotype='in', desc='Power in approximation equation for buckling stability') kgc = Float( iotype='in', desc= 'Buckling coefficient for component general buckling of stiffener web panel' ) kgw = Float( iotype='in', desc='Buckling coefficient for component local buckling of web panel') # KCONT(12) ! Structural Geometry Concept Top/Bottom # KCONB(12) ! 2 - Simply stiffened shell, frames, sized for minimum weight in buckling # ! 3 - Z-stiffened shell, frames, best buckling # ! 4 - Z-stiffened shell, frames, buckling-minimum gage compromise # ! 5 - Z-stiffened shell, frames, buckling-pressure compromise # ! 6 - Truss-core sandwich, frames, best buckling # ! 8 - Truss-core sandwich, no frames, best buckling # ! 9 - Truss-core sandwich, no frames, buckling-min. gage-pressure compromise kcont = Enum([2, 3, 4, 5, 6, 8, 9], iotype='in', desc='Structural Geometry Concept Top') kconb = Enum([2, 3, 4, 5, 6, 8, 9], iotype='in', desc='Structural Geometry Concept Bottom') # Material properties # ------------------- ftst = Float(iotype='in', desc="Tensile Strength on Top") ftsb = Float(iotype='in', desc="Tensile Strength on Bottom") fcst = Float(iotype='in', desc="Compressive Strength on Top") fcsb = Float(iotype='in', desc="Compressive Strength on Bottom") est = Float(iotype='in', desc="Young's Modulus for the shells Top") esb = Float(iotype='in', desc="Young's Modulus for the shells Bottom") eft = Float(iotype='in', desc="Young's Modulus for the frames Top") efb = Float(iotype='in', desc="Young's Modulus for the frames Bottom") dst = Float(iotype='in', desc="Density of shell material on Top") dsb = Float(iotype='in', desc="Density of shell material on Bottom") dft = Float(iotype='in', desc="Density of frame material on Top") dfb = Float(iotype='in', desc="Density of frame material on Bottom") tmgt = Float(iotype='in', desc="Minimum gage thickness Top") tmgb = Float(iotype='in', desc="Minimum gage thickness Bottom") kde = Float(iotype='in', desc="Knock-down factor for modulus") kdf = Float(iotype='in', desc="Knock-down factor for strength") # Geometric parameters # -------------------- clbr1 = Float( iotype='in', desc='Fuselage break point as a fraction of total fuselage length') icyl = Enum( [1, 0], iotype='in', desc= ' 1 - modeled with a mid-body cylinder, 0 - use two power-law bodies back to back' ) # Engines # -------------------- neng = Int(iotype='in', desc=' Total number of engines') nengwing = Int(iotype='in', desc=' Number of engines on wing') wfp = Float(iotype='in', desc='(Engine Weight * NENG) / WGTO') clrw1 = Float( iotype='in', desc=' Location of first engine pair. Input 0 for centerline engine.') clrw2 = Float( iotype='in', desc=' Location of second engine pair. measured from body centerline') clrw3 = Float( iotype='in', desc=' Location of third engine pair. measured from body centerline') # Loads # -------------------- deslf = Float(iotype='in', desc='Design load factor') ultlf = Float(iotype='in', desc='Ultimate load factor (usually 1.5*DESLF)') axac = Float(iotype='in', desc='Axial acceleration') cman = Float(iotype='in', desc=' Weight fraction at maneuver') iload = Enum( [1, 2, 3], iotype='in', desc= '1 - Analyze maneuver only; 2 - Analyze maneuver and landing only; 3 - Analyze bump, landing and maneuver' ) pgt = Float(iotype='in', desc="Fuselage gage pressure on top") pgb = Float(iotype='in', desc="Fuselage gage pressure on bottom") wfbump = Float(iotype='in', desc=' Weight fraction at bump') wfland = Float(iotype='in', desc=' Weight fraction at landing') # Landing Gear # ------------------- vsink = Float(iotype='in', units='ft/s', desc='Design sink velocity at landing ') stroke = Float(iotype='in', units='ft', desc=' Stroke of landing gear ') clrg1 = Float( iotype='in', desc= 'Length fraction of nose landing gear measured as a fraction of total fuselage length' ) clrg2 = Float( iotype='in', desc= 'Length fraction of main landing gear measured as a fraction of total fuselage length' ) wfgr1 = Float(iotype='in', desc='Weight fraction of nose landing gear') wfgr2 = Float(iotype='in', desc='Weight fraction of main landing gear') igear = Enum( [1, 2], iotype='in', desc= '1 - Main landing gear located on fuselage,2 - Main landing gear located on wing' ) gfrl = Float( iotype='in', desc= 'Ratio of force taken by nose landing gear to force taken by main gear at landing' ) clrgw1 = Float( iotype='in', desc='Position of wing gear as a fraction of structural semispan') clrgw2 = Float( iotype='in', desc= 'Position of second pair wing gear as a fraction of structural semispan' ) # Weights # ------------------- wgto = Float(iotype='in', units='lb', desc=' Gross takeoff weight') wtff = Float(iotype='in', desc='Weight fraction of fuel') cbum = Float(iotype='in', desc='Weight fraction at bump') clan = Float(iotype='in', desc='Weight fraction at landing') # Factors # -------------------- ischrenk = Int( iotype='in', desc= '1 - use Schrenk load distribution on wing,Else - use trapezoidal distribution' ) icomnd = Enum( [1, 2], iotype='in', desc= '1 - print gross shell dimensions envelope,2 - print detailed shell geometry' ) wgno = Float( iotype='in', desc='Nonoptimal factor for wing (including the secondary structure)') slfmb = Float(iotype='in', desc='Static load factor for bumps') wmis = Float(iotype='in', desc='Volume component of secondary structure') wsur = Float(iotype='in', desc='Surface area component of secondary structure') wcw = Float(iotype='in', desc='Factor in weight equation for nonoptimal weights') wca = Float(iotype='in', desc='Factor in weight equation for nonoptimal weights') nwing = Int(iotype='in', desc='Number of wing segments for analysis') # Outputs # -------------------- wfuselaget = Float(iotype='out', units='lb', desc='Total fuselage weight') wwingt = Float(iotype='out', units='lb', desc='Total wing weight') def __init__(self): """Constructor for the PdcylComp component""" super(PdcylComp, self).__init__() # External Code public variables self.stdin = 'PDCYL.in' self.stdout = 'PDCYL.out' self.stderr = 'PDCYL.err' self.command = ['PDCYL'] self.external_files = [ FileMetadata(path=self.stdin, input=True), FileMetadata(path=self.stdout), FileMetadata(path=self.stderr), ] # Dictionary contains location of every numeric scalar variable fields = {} fields[8] = 'wsweep' fields[9] = 'war' fields[10] = 'wtaper' fields[11] = 'wtcroot' fields[12] = 'wtctip' fields[13] = 'warea' fields[15] = 'ps' fields[16] = 'tmgw' fields[17] = 'effw' fields[18] = 'effc' fields[19] = 'esw' fields[20] = 'fcsw' fields[21] = 'dsw' fields[22] = 'kdew' fields[23] = 'kdfw' fields[25] = 'istama' fields[27] = 'cs1' fields[28] = 'cs2' fields[29] = 'uwwg' fields[30] = 'xwloc1' fields[32] = 'claqr' fields[33] = 'ifuel' fields[35] = 'cwman' fields[36] = 'cf' fields[40] = 'itail' fields[42] = 'uwt' fields[43] = 'clrt' fields[44] = 'harea' fields[49] = 'frn' fields[50] = 'frab' fields[51] = 'bodl' fields[52] = 'bdmax' fields[54] = 'ckf' fields[55] = 'ec' fields[56] = 'kgc' fields[57] = 'kgw' fields[58] = 'kcont' fields[59] = 'kconb' fields[67] = 'ftst' fields[68] = 'ftsb' fields[69] = 'fcst' fields[70] = 'fcsb' fields[71] = 'est' fields[72] = 'esb' fields[73] = 'eft' fields[74] = 'efb' fields[75] = 'dst' fields[76] = 'dsb' fields[77] = 'dft' fields[78] = 'dfb' fields[79] = 'tmgt' fields[80] = 'tmgb' fields[81] = 'kde' fields[82] = 'kdf' fields[84] = 'clbr1' fields[85] = 'icyl' fields[90] = 'neng' fields[91] = 'nengwing' fields[92] = 'wfp' fields[93] = 'clrw1' fields[95] = 'clrw2' fields[96] = 'clrw3' fields[100] = 'deslf' fields[101] = 'ultlf' fields[102] = 'axac' fields[103] = 'cman' fields[104] = 'iload' fields[107] = 'pgt' fields[108] = 'pgb' fields[109] = 'wfbump' fields[110] = 'wfland' fields[114] = 'vsink' fields[115] = 'stroke' fields[116] = 'clrg1' fields[117] = 'clrg2' fields[118] = 'wfgr1' fields[119] = 'wfgr2' fields[120] = 'igear' fields[122] = 'gfrl' fields[123] = 'clrgw1' fields[124] = 'clrgw2' fields[129] = 'wgto' fields[130] = 'wtff' fields[131] = 'cbum' fields[132] = 'clan' fields[136] = 'ischrenk' fields[138] = 'icomnd' fields[140] = 'wgno' fields[141] = 'slfmb' fields[142] = 'wmis' fields[143] = 'wsur' fields[144] = 'wcw' fields[145] = 'wca' fields[146] = 'nwing' self._fields = fields def execute(self): """Run PDCYL.""" #Prepare the input file for PDCYL self.generate_input() #Run PDCYL via ExternalCode's execute function super(PdcylComp, self).execute() #Parse the outut file from PDCYL self.parse_output() def generate_input(self): """Creates the PDCYL custom input file.""" data = [] form = "%.15g %s\n" # It turns out to be simple and quick to generate a new input file each # time, rather than poking values into a template. data.append("\n\n") data.append(self.title) data.append("\n\n") if self.icalc == True: icalc = 3 else: icalc = 0 data.append("%d icalc print switch" % icalc) data.append("\n\n\n") data.append("Wing geometry:\n") for nline in range(8, 14): name = self._fields[nline] data.append(form % (self.get(name), name)) data.append("Material properties:\n") for nline in range(15, 24): name = self._fields[nline] data.append(form % (self.get(name), name)) data.append("Geometric properties:\n") name = self._fields[25] data.append(form % (self.get(name), name)) data.append("\n") for nline in range(27, 31): name = self._fields[nline] data.append(form % (self.get(name), name)) data.append("Structural concept:\n") for nline in range(32, 34): name = self._fields[nline] data.append(form % (self.get(name), name)) data.append("\n") for nline in range(35, 37): name = self._fields[nline] data.append(form % (self.get(name), name)) data.append("\n\n") data.append("Tails:\n") name = self._fields[40] data.append(form % (self.get(name), name)) data.append("\n") for nline in range(42, 45): name = self._fields[nline] data.append(form % (self.get(name), name)) data.append("\n\n\n") data.append("Fuselage geometry:\n") for nline in range(49, 53): name = self._fields[nline] data.append(form % (self.get(name), name)) data.append("Structural concept:\n") for nline in range(54, 60): name = self._fields[nline] data.append(form % (self.get(name), name)) data.append("\n\n\n\n\n\n") data.append("Material properties:\n") for nline in range(67, 83): name = self._fields[nline] data.append(form % (self.get(name), name)) data.append("Geometric parameters:\n") for nline in range(84, 86): name = self._fields[nline] data.append(form % (self.get(name), name)) data.append("\n\n\n") data.append("Engines:\n") for nline in range(90, 94): name = self._fields[nline] data.append(form % (self.get(name), name)) data.append("\n") for nline in range(95, 97): name = self._fields[nline] data.append(form % (self.get(name), name)) data.append("\n\n") data.append("Loads:\n") for nline in range(100, 105): name = self._fields[nline] data.append(form % (self.get(name), name)) data.append("\n\n") for nline in range(107, 111): name = self._fields[nline] data.append(form % (self.get(name), name)) data.append("\n\n") data.append("Landing gear:\n") for nline in range(114, 121): name = self._fields[nline] data.append(form % (self.get(name), name)) data.append("\n\n") for nline in range(122, 125): name = self._fields[nline] data.append(form % (self.get(name), name)) data.append("\n\n\n") data.append("Weights:\n") for nline in range(129, 133): name = self._fields[nline] data.append(form % (self.get(name), name)) data.append("\n\n") data.append("Factors:\n") name = self._fields[136] data.append(form % (self.get(name), name)) data.append("\n") name = self._fields[138] data.append(form % (self.get(name), name)) data.append("\n") for nline in range(140, 147): name = self._fields[nline] data.append(form % (self.get(name), name)) outfile = open(self.stdin, 'w') outfile.writelines(data) outfile.close() def parse_output(self): """Parses the PCYL output file and extracts data.""" infile = FileParser() infile.set_file(self.stdout) self.wwingt = infile.transfer_keyvar("Total Wing Structural Weight", 1) self.wfuselaget = infile.transfer_keyvar( "Fuselage Total Structural Weight", 1) def load_model(self, filename): """Reads in an existing PDCYL input file and populates the variable tree with its values.""" infile = FileParser() infile.set_file(filename) # Title is a string self.title = infile.transfer_line(2) # Print flag becomes a Bool if infile.transfer_var(4, 1) == 3: self.icalc = True else: self.icalc = False # Named variables in dictionary for key, val in self._fields.iteritems(): self.set(val, infile.transfer_var(key, 1))
def __init__(self, *args, **kwargs): super(MyComponent, self).__init__(*args, **kwargs) self.add('cont', Container()) self.cont.add('dyntrait', Float(3.))
def __init__(self, nTurbines, nDirections, optimize_position=False, nSamples=0, optimize_yaw=False, datasize=0, nSpeeds=False, maxiter=100): super(floris_assembly_opt_AEP, self).__init__() if nSpeeds == False: nSpeeds = nDirections self.nTurbines = nTurbines self.nSamples = nSamples self.nDirections = nDirections self.optimize_yaw = optimize_yaw self.optimize_position = optimize_position self.datasize = datasize self.nSpeeds = nSpeeds self.maxiter = maxiter # wt_layout input variables self.add( 'rotorDiameter', Array(np.zeros(nTurbines), dtype='float', iotype='in', units='m', desc='rotor diameters of all turbine')) self.add( 'axialInduction', Array(np.zeros(nTurbines), iotype='in', dtype='float', desc='axial induction of all turbines')) self.add('hubHeight', Array(np.zeros(nTurbines), dtype='float', iotype='in', units='m', \ desc='hub heights of all turbines')) # turbine properties for ccblade and pre-calculated controller self.add( 'curve_CP', Array(np.zeros(datasize), iotype='in', desc='pre-calculated CPCT')) self.add( 'curve_CT', Array(np.zeros(datasize), iotype='in', desc='pre-calculated CPCT')) self.add( 'curve_wind_speed', Array(np.zeros(datasize), iotype='in', desc='pre-calculated CPCT')) self.add('initVelocitiesTurbines', Array(np.zeros(nTurbines), iotype='in', units='m/s')) self.add( 'generator_efficiency', Array(np.zeros(nTurbines), iotype='in', dtype='float', desc='generator efficiency of all turbines')) self.add( 'turbineX', Array(np.zeros(nTurbines), iotype='in', dtype='float', desc='x positions of turbines in original ref. frame')) self.add( 'turbineY', Array(np.zeros(nTurbines), iotype='in', dtype='float', desc='y positions of turbines in original ref. frame')) if optimize_yaw: for direction in range(0, nDirections): self.add('yaw_%d' % direction, Array(np.zeros(nTurbines), iotype='in', dtype='float', \ desc='yaw of each turbine for each direction')) else: self.add('yaw', Array(np.zeros(nTurbines), iotype='in', dtype='float', \ desc='yaw of each turbine')) # windrose input variables self.add( 'windrose_directions', Array(np.zeros(nDirections), dtype='float', iotype='in', desc='windrose directions in degrees ccw from east')) self.add( 'windrose_frequencies', Array( np.ones(nDirections), dtype='float', iotype='in', desc='windrose frequencies corresponding to windrose_directions' )) if nSpeeds == 1: self.add( 'windrose_speeds', Float( iotype='in', units='m/s', desc= 'wind speeds for each direction given in windrose_directions' )) else: self.add( 'windrose_speeds', Array( np.zeros(nDirections), dtype='float', iotype='in', units='m/s', desc= 'wind speeds for each direction given in windrose_directions' )) # Explicitly size output arrays # variables added to test individual components self.add( 'turbineXw', Array( np.zeros(nTurbines), iotype='out', units='m', desc= 'X positions of turbines in the wind direction reference frame' )) self.add( 'turbineYw', Array( np.zeros(nTurbines), iotype='out', units='m', desc= 'Y positions of turbines in the wind direction reference frame' )) self.add( 'wakeCentersYT', Array(np.zeros(nTurbines), dtype='float', iotype='out', units='m', desc='centers of the wakes at each turbine')) self.add( 'wakeDiametersT', Array(np.zeros(nTurbines), dtype='float', iotype='out', units='m', desc='diameters of each of the wake zones for each of the \ wakes at each turbine')) self.add( 'wakeOverlapTRel', Array(np.zeros(nTurbines), dtype='float', iotype='out', units='m', desc='ratio of overlap area of each zone to rotor area')) # standard output self.add( 'velocitiesTurbines_directions', Array(np.zeros([nDirections, nTurbines]), iotype='out', units='m/s', dtype='float', desc='effective windspeed at each turbine \ in each direction ccw from east using direction to' )) self.add( 'wt_power_directions', Array(np.zeros([nDirections, nTurbines]), iotype='out', units='kW', dtype='float', desc='power of each turbine in each direction ccw from \ east using direction to')) self.add( 'power_directions', Array(np.zeros(nDirections), iotype='out', units='kW', desc='total windfarm power \ in each direction ccw from east using direction to' )) if nSamples > 0: # flow samples self.add( 'ws_positionX', Array(np.zeros(nSamples), iotype='in', units='m', desc='X positions of sampling points')) self.add( 'ws_positionY', Array(np.zeros(nSamples), iotype='in', units='m', desc='Y position of sampling points')) self.add( 'ws_positionZ', Array(np.zeros(nSamples), iotype='in', units='m', desc='Z position of sampling points')) for direction in range(0, nDirections): self.add( 'ws_array_%d' % direction, Array(np.zeros(nSamples), iotype='out', units='m/s', desc='predicted wind speed at sampling points'))
class DumbVT(VariableTree): v1 = Float(1., desc='vv1') v2 = Float(2., desc='vv2') vt2 = VarTree(DumbVT2(), iotype='in')
class DumbVT2(VariableTree): x = Float(-1.) y = Float(-2.) vt3 = VarTree(DumbVT3())
class Input_List(Component): SYS_list = ['VL_SYS', 'FWD_SYS', 'WING_SYS', 'ENG_SYS'] #a list of systems ASPECT_list = ['VL_SYS_TYPE', 'VL_SYS_PROP', 'VL_SYS_DRV', 'VL_SYS_TECH', \ 'FWD_SYS_PROP', 'FWD_SYS_DRV', 'FWD_SYS_TYPE',\ 'WING_SYS_TYPE', \ 'ENG_SYS_TYPE'] #list of system functional aspects input_file = Str('', iotype='in', desc='input csv file with morph matrix data') #options = List([], iotype='in', desc='list of integers representing options for a given alternative') option1 = Float(1, iotype='in', low=0.5, high=6.5, desc='option selection for functional aspect VL_SYS_TYPE (1-6)') option2 = Float(1, iotype='in', low=0.5, high=3.5, desc='option selection for functional aspect VL_SYS_PROP (1-3)') option3 = Float(1, iotype='in', low=0.5, high=3.5, desc='option selection for functional aspect VL_SYS_DRV (1-3)') option4 = Float(1, iotype='in', low=0.5, high=5.5, desc='option selection for functional aspect VL_SYS_TECH (1-5)') option5 = Float(1, iotype='in', low=0.5, high=4.5, desc='option selection for functional aspect FWD_SYS_PROP (1-4)') option6 = Float(1, iotype='in', low=0.5, high=3.5, desc='option selection for functional aspect FWD_SYS_DRV (1-3)') option7 = Float(1, iotype='in', low=0.5, high=4.5, desc='option selection for functional aspect FWD_SYS_TYPE (1-4)') option8 = Float(1, iotype='in', low=0.5, high=6.5, desc='option selection for functional aspect WING_SYS_TYPE (1-6)') option9 = Float(1, iotype='in', low=0.5, high=4.5, desc='option selection for functional aspect ENG_SYS_TYPE (1-4)') passthrough = Int(0, iotype='in', low=0, high=1, desc='passthrough flag for incompatible options') ### LIST INPUTS GENERATED (OUTPUTS) HERE ### #PHI SYSTEM INPUTS: #VL_SYS_TYPE_w = List(['VL_SYS_TYPE_w'], iotype='out', desc='') #VL_SYS_TYPE_e_d = List(['VL_SYS_TYPE_e_d'], iotype='out', desc='') #VL_SYS_PROP_w = List(['VL_SYS_PROP_w'], iotype='out', desc='') #FWD_SYS_PROP_eta_p = List(['FWD_SYS_PROP_eta_p'], iotype='out', desc='') #WING_SYS_TYPE_phi = List(['WING_SYS_TYPE_phi'], iotype='out', desc='') #WING_SYS_TYPE_LD = List(['WING_SYS_TYPE_LD'], iotype='out', desc='') #ENG_SYS_TYPE_phi = List(['ENG_SYS_TYPE_phi'], iotype='out', desc='') #UPDATED VL_SYS_TYPE_phi = List(['VL_SYS_TYPE_phi'], iotype='out', desc='') VL_SYS_TYPE_w = List(['VL_SYS_TYPE_w'], iotype='out', desc='') VL_SYS_TYPE_f = List(['VL_SYS_TYPE_f'], iotype='out', desc='') VL_SYS_PROP_phi = List(['VL_SYS_PROP_phi' ], iotype='out', desc='') VL_SYS_PROP_w = List(['VL_SYS_PROP_w' ], iotype='out', desc='') VL_SYS_TECH_phi = List(['VL_SYS_TECH_phi'], iotype='out', desc='') VL_SYS_TECH_w = List(['VL_SYS_TECH_w'], iotype='out', desc='') VL_SYS_TECH_f = List(['VL_SYS_TECH_f'], iotype='out', desc='') VL_SYS_TECH_LD = List(['VL_SYS_TECH_LD'], iotype='out', desc='') FWD_SYS_PROP_eta_p = List(['FWD_SYS_PROP_eta_p'], iotype='out', desc='') FWD_SYS_DRV_eta_d = List(['FWD_SYS_DRV_eta_d'], iotype='out', desc='') FWD_SYS_TYPE_phi = List(['FWD_SYS_TYPE_phi'], iotype='out', desc='') FWD_SYS_TYPE_TP = List(['FWD_SYS_TYPE_TP'], iotype='out', desc='') WING_SYS_TYPE_LD = List(['WING_SYS_TYPE_LD'], iotype='out', desc='') WING_SYS_TYPE_f = List(['WING_SYS_TYPE_f'], iotype='out', desc='') #LoD SYSTEM INPUTS: SYSTEM_f = List(['SYSTEM_f'], iotype='out', desc='average system flat plate drag (fuzzy gauss)') WING_LoD = List(['WING_LoD'], iotype='out', desc='union of all LoD values (fuzzy gauss)') #FoM SYSTEM INPUTS: VL_SYS_w = List(['VL_SYS_w'], iotype='out', desc='') VL_SYS_PROP_sigma = List(['VL_SYS_PROP_sigma'], iotype='out', desc='') VL_SYS_e_d = List(['VL_SYS_e_d'], iotype='out', desc='') VL_SYS_DRV_eta_d = List(['VL_SYS_DRV_eta_d'], iotype='out', desc='') #Propulsive Efficiency INPUTS: FWD_SYS_eta_p = List(['FWD_SYS_eta_p'], iotype='out', desc='') FWD_DRV_eta_d = List(['FWD_DRV_eta_d'], iotype='out', desc='') #RF System INPUTS: WING_SYS_TYPE_WS = List(['WING_SYS_TYPE_WS'], iotype='out', desc='') SYS_type = List(['VL_type'], iotype='out', desc='') SYS_tech = List(['VL_tech'], iotype='out', desc='') ENG_SYS_TYPE_SFC = List(['ENG_SYS_TYPE_SFC'], iotype='out', desc='') #def __init__(self): """ Initialize component """ #super(Input_List, self).__init__() data = [] #list for input data options = [] #place holder for selected options ### def read_fuzzy_data(self): """ Read the (morph) input file and store as a list for pulling data from """ #input_file = self.input_file print 'Reading', self.input_file, 'data file and translating inputs.' with open(self.input_file, 'rU') as csvfile: input_reader = csv.reader(csvfile, delimiter=',') data = [] for row in input_reader: #read each row if row[2] <> '': #if variable is there... data_row = [] for x in row: #for each item in the row if '[' in x: #check for '[min,max]' entry y = x.strip(' []').split(',') #remove brackets from string and split at comma if '.' in y: y[y.index('.')] = 0.0 data_row.append([ float(y[0]), float(y[1]) ]) #add data min/max as floats to list else: data_row.append(x) data.append(data_row) if len(data)>1: data.pop(0) #remove header line self.data = data #save data as output var print len(self.data), 'lines of input data read... inputs translated.' def execute(self): #print "Getting: ", [self.option1, self.option2, self.option3, self.option4, self.option5, self.option6, self.option7, self.option8, self.option9] #if no data read in, read it in. if len(self.data) == 0: self.read_fuzzy_data() #set options from individual functional attibutes self.options = [int(self.option1), int(self.option2), int(self.option3), int(self.option4), int(self.option5), int(self.option6), int(self.option7), int(self.option8), int(self.option9)] #print "Morph Opts:", self.options #print 'Building input list from', len(self.data), 'lines of data...' #get all inputs for selected options #[ system, aspect, varname, [min,max], quant_option, qual_option ] for each line var_list = [] for line in self.data: var_list.append([ line[0], line[1], line[3], line[4], \ line[self.options[self.ASPECT_list.index(line[1])]+4], \ line[self.options[self.ASPECT_list.index(line[1])]+10] ]) ### CALCULATE INPUTS: (all use quant data: qual data => q = 10) q = 4 #for quant data, qual data in q=5 """ PHI SYSTEM: """ fuzzInType = 'gauss' #VL_SYS_TYPE_phi: _x = next( var[q] for var in var_list if all((var[2] == 'phi', var[1] == 'VL_SYS_TYPE')) ) self.VL_SYS_TYPE_phi = fuzzyOps.rangeToMF(_x, fuzzInType) #VL_SYS_TYPE_w : _x = next( var[q] for var in var_list if all((var[2] == 'w', var[1] == 'VL_SYS_TYPE')) ) self.VL_SYS_TYPE_w = fuzzyOps.rangeToMF(_x, fuzzInType) #VL_SYS_TYPE_f _x = next( var[q] for var in var_list if all((var[2] == 'f', var[1] == 'VL_SYS_TYPE')) ) self.VL_SYS_TYPE_f = fuzzyOps.rangeToMF(_x, fuzzInType) #'VL_SYS_PROP_phi' _x = next( var[q] for var in var_list if all((var[2] == 'phi', var[1] == 'VL_SYS_PROP')) ) self.VL_SYS_PROP_phi = fuzzyOps.rangeToMF(_x, fuzzInType) #'VL_SYS_PROP_w' _x = next( var[q] for var in var_list if all((var[2] == 'w', var[1] == 'VL_SYS_PROP')) ) self.VL_SYS_PROP_w = fuzzyOps.rangeToMF(_x, fuzzInType) #'VL_SYS_TECH_phi' _x = next( var[q] for var in var_list if all((var[2] == 'phi', var[1] == 'VL_SYS_TECH')) ) self.VL_SYS_TECH_phi = fuzzyOps.rangeToMF(_x, fuzzInType) #'VL_SYS_TECH_w' _x = next( var[q] for var in var_list if all((var[2] == 'w', var[1] == 'VL_SYS_TECH')) ) self.VL_SYS_TECH_w = fuzzyOps.rangeToMF(_x, fuzzInType) #'VL_SYS_TECH_f' _x = next( var[q] for var in var_list if all((var[2] == 'f', var[1] == 'VL_SYS_TECH')) ) self.VL_SYS_TECH_f = fuzzyOps.rangeToMF(_x, fuzzInType) #'VL_SYS_TECH_LD' _x = next( var[q] for var in var_list if all((var[2] == 'LD', var[1] == 'VL_SYS_TECH')) ) self.VL_SYS_TECH_LD = fuzzyOps.rangeToMF(_x, fuzzInType) #FWD_SYS_PROP_eta_p : FWD system prop efficiency _x = next( var[q] for var in var_list if all((var[2] == 'eta_p', var[1] == 'FWD_SYS_PROP')) ) self.FWD_SYS_PROP_eta_p = fuzzyOps.rangeToMF(_x, fuzzInType) #FWD_SYS_DRV_eta_d : FWD drive efficiency _x = next( var[q] for var in var_list if all((var[2] == 'eta_d', var[1] == 'FWD_SYS_DRV')) ) self.FWD_SYS_DRV_eta_d = fuzzyOps.rangeToMF(_x, fuzzInType) #FWD_SYS_TYPE_phi _x = next( var[q] for var in var_list if all((var[2] == 'phi', var[1] == 'FWD_SYS_TYPE')) ) self.FWD_SYS_TYPE_phi = fuzzyOps.rangeToMF(_x, fuzzInType) #FWD_SYS_TYPE_TP _x = next( var[q] for var in var_list if all((var[2] == 'TP', var[1] == 'FWD_SYS_TYPE')) ) self.FWD_SYS_TYPE_TP = fuzzyOps.rangeToMF(_x, fuzzInType) #WING_SYS_TYPE_LD _x = next( var[q] for var in var_list if all((var[2] == 'LD', var[1] == 'WING_SYS_TYPE')) ) self.WING_SYS_TYPE_LD = fuzzyOps.rangeToMF(_x, fuzzInType) #WING_SYS_TYPE_f : WING system wing loading _x = next( var[q] for var in var_list if all((var[2] == 'f', var[1] == 'WING_SYS_TYPE')) ) self.WING_SYS_TYPE_f = fuzzyOps.rangeToMF(_x, fuzzInType) #ENG_SYS_TYPE_SFC _x = next( var[q] for var in var_list if all((var[2] == 'SFC', var[1] == 'ENG_SYS_TYPE')) ) self.ENG_SYS_TYPE_SFC = fuzzyOps.rangeToMF(_x, fuzzInType) """ LoD SYSTEM: """ fuzzInType = 'trap' # SYSTEM_f : average system flat plate drag (fuzzy gauss) _f = [var[q] for var in var_list if (var[2] == 'f') ] data_range = [np.average([v[0] for v in _f]), np.average([v[1] for v in _f])] #get union self.SYSTEM_f = fuzzyOps.rangeToMF(data_range, fuzzInType) #WING_LoD : union of all LoD values (fuzzy gauss) _ld = [var[q] for var in var_list if var[2] == 'LD'] data_range = [max([v[0] for v in _ld]), min([v[1] for v in _ld])] #get union self.WING_LoD = fuzzyOps.rangeToMF(data_range, fuzzInType) """ FOM SYSTEM: """ fuzzInType = 'gauss' #VL_SYS_w #_x = [var[q] for var in var_list if all((var[2] == 'w', var[0] == 'VL_SYS'))] #_x = [ np.average([x[0] for x in _x]), np.average([x[1] for x in _x]) ] _x1 = next( var[q] for var in var_list if all((var[2] == 'w', var[1] == 'VL_SYS_TYPE')) ) _x2 = next( var[q] for var in var_list if all((var[2] == 'w', var[1] == 'VL_SYS_PROP')) ) _x3 = next( var[q] for var in var_list if all((var[2] == 'w', var[1] == 'VL_SYS_TECH')) ) _x = [ max(np.average([_x1[0],_x2[0]]), _x3[0]), min(np.average([_x1[1],_x2[1]]),_x3[1]) ] self.VL_SYS_w = fuzzyOps.rangeToMF(_x, fuzzInType) _w = _x #VL_SYS_PROP_sigma _x = next( var[q] for var in var_list if all((var[2] == 'sigma', var[1] == 'VL_SYS_PROP')) ) self.VL_SYS_PROP_sigma = fuzzyOps.rangeToMF(_x, fuzzInType) #x_2 = _x #VL_SYS_e_d _x = next( var[q] for var in var_list if all((var[2] == 'e_d', var[1] == 'VL_SYS_TYPE')) ) self.VL_SYS_e_d = fuzzyOps.rangeToMF(_x, fuzzInType) _ed = _x #VL_SYS_DRV_eta_d _x = next( var[q] for var in var_list if all((var[2] == 'eta_d', var[1] == 'VL_SYS_DRV')) ) self.VL_SYS_DRV_eta_d = fuzzyOps.rangeToMF(_x, fuzzInType) _eta = _x #print 'w: %s, sigma: %s, e_d: %s, eta_d: %s' % (x_1, x_2, x_3, x_4) """ etaP SYSTEM: """ fuzzInType = 'trap' # FWD_SYS_eta_p : intersection of forward system propulsive efficiencies _f = [var[q] for var in var_list if all((var[2] == 'eta_p', var[0] == 'FWD_SYS')) ] data_range = [max([v[0] for v in _f]), min([v[1] for v in _f])] #get union data_range = sorted(data_range) self.FWD_SYS_eta_p = fuzzyOps.rangeToMF(data_range, fuzzInType) #FWD_SYS_eta_d : foward system drive efficiency _etad = next( var[q] for var in var_list if all((var[2] == 'eta_d', var[1] == 'FWD_SYS_DRV')) ) self.FWD_DRV_eta_d = fuzzyOps.rangeToMF(_etad, fuzzInType) """ RF SYSTEMs (GWT/Pinst/VH): """ # SYSTEM_QUANT_PHI # (from phi system) # NEEDS TO BE QUANTIFIED # VL_SYS_w # self.VL_SYS_w (already calculatd with FoM system) # WING_SYS_TYPE_WS : WING system wing loading _x = next( var[q] for var in var_list if all((var[2] == 'WS', var[1] == 'WING_SYS_TYPE')) ) self.WING_SYS_TYPE_WS = fuzzyOps.rangeToMF(_x, 'gauss') # sys_etaP: system propulsive efficiency # (from etaP system) # VL_SYS_DRV_eta_d : VL system drive efficiency # VL_SYS_DRV_eta_d (already calcualted with FoM system) # sys_FoM: system Figure of Merit # (from FoM system) # VL_SYS_e_d # self.VL_SYS_e_d (already calcualted with FoM system) # ENG_SYS_TYPE_SFC # self.ENG_SYS_TYPE_SFC (already calcualted with phi system) # NEEDS TO BE QUANTIFIED? # SYS_TYPE (1-tilt, 2-compound, 3-other) VL_SYS_TYPE = int(self.option1) FWD_SYS_TYPE = int(self.option7) if FWD_SYS_TYPE == 2: T = 1 #tiling VL else: if VL_SYS_TYPE < 4: T = 2 #compound if VL_SYS_TYPE == 4 or VL_SYS_TYPE == 5: T = 3 #other if VL_SYS_TYPE == 6: T = 1 #tilting tailsitter self.SYS_type = fuzzyOps.rangeToMF([T,T], 'gauss') # SYS_TECH (0 - None, 1 - varRPM, 2 - varDiameter, 3 - stop rotor, 4 - autogyro) (switch 2-3) VL_SYS_TECH = int(self.option4) if VL_SYS_TECH == 2: T = 3 elif VL_SYS_TECH == 3: T = 2 else: T = VL_SYS_TECH self.SYS_tech = fuzzyOps.rangeToMF([T,T], 'gauss') if self.passthrough == 1: #catch for incompatible options return None
class SellarBLISS2000(Assembly): """ Optimization of the Sellar problem using the BLISS2000 algorithm Disciplines coupled with FixedPointIterator. """ # for a given iteration, x1_store holds the value of dis1.x1 obtained in the previous iteration. used to track convergence x1_store = Float(0.0, iotype="in") z1_store = Float(0.0, iotype="in") z2_store = Float(0.0, iotype="in") def configure(self): """ Creates a new Assembly with this problem Optimal Design at (1.9776, 0, 0) Optimal Objective = 3.18339""" # objective = '(dis1.x1)**2 + dis1.z2 + dis1.y1 + exp(-dis2.y2)' # constraint1 = 'dis1.y1 > 3.16' # constraint2 = 'dis2.y2 < 24.0' # Metamodel for sellar discipline 1 self.add("meta_model_dis1", MetaModel()) self.meta_model_dis1.surrogates = {"y1": ResponseSurface()} self.meta_model_dis1.model = SellarDiscipline1() self.meta_model_dis1.recorder = DBCaseRecorder() # Metamodel for sellar discipline 2 self.add("meta_model_dis2", MetaModel()) self.meta_model_dis2.surrogates = {"y2": ResponseSurface()} self.meta_model_dis2.model = SellarDiscipline2() self.meta_model_dis2.recorder = DBCaseRecorder() # training metalmodel for disc1 # self.add("DOE_Trainer_dis2",NeighborhoodDOEdriver()) # self.DOE_Trainer_dis2.DOEgenerator = CentralComposite() # self.DOE_Trainer_dis2.alpha = .1 # self.DOE_Trainer_dis2.add_parameter("meta_model_dis2.z1",low=-10,high=10,start=5.0) # self.DOE_Trainer_dis2.add_parameter("meta_model_dis2.z2",low=0,high=10,start=2.0) # self.DOE_Trainer_dis2.add_parameter("meta_model_dis2.y1",low=0,high=20) # self.DOE_Trainer_dis2.add_event("meta_model_dis2.train_next") # optimization of global objective function self.add('sysopt', SLSQPdriver()) self.sysopt.add_objective( '(meta_model_dis1.x1)**2 + meta_model_dis1.z2 + meta_model_dis1.y1 + math.exp(-meta_model_dis2.y2)' ) self.sysopt.add_parameter(['meta_model_dis1.z1', 'meta_model_dis2.z1'], low=-10, high=10.0, start=5.0) self.sysopt.add_parameter(['meta_model_dis1.z2', 'meta_model_dis2.z2'], low=0, high=10.0, start=2.0) self.sysopt.add_parameter('meta_model_dis1.y2', low=-1e99, high=1e99) self.sysopt.add_parameter('meta_model_dis2.y1', low=-1e99, high=1e99) # feasibility constraints self.sysopt.add_constraint('meta_model_dis1.y2 <= meta_model_dis2.y2') self.sysopt.add_constraint('meta_model_dis1.y2 >= meta_model_dis2.y2') self.sysopt.add_constraint('meta_model_dis2.y1 <= meta_model_dis1.y1') self.sysopt.add_constraint('meta_model_dis2.y1 >= meta_model_dis1.y1') self.sysopt.add_constraint('3.16 < meta_model_dis1.y1') self.sysopt.add_constraint('meta_model_dis2.y2 < 24.0') # optimization of discipline 1 (discipline 2 of the sellar problem has no local variables) self.add('local_opt_dis1', SLSQPdriver()) self.local_opt_dis1.add_objective('meta_model_dis1.y1') self.local_opt_dis1.add_parameter('meta_model_dis1.x1', low=0, high=10.0) self.local_opt_dis1.add_constraint('3.16 < meta_model_dis1.y1') self.local_opt_dis1.add_event('meta_model_dis1.train_next') self.local_opt_dis1.workflow.add(['meta_model_dis1']) # training metalmodel for disc1 self.add("DOE_Trainer_dis1", NeighborhoodDOEdriver()) self.DOE_Trainer_dis1.DOEgenerator = CentralComposite() self.DOE_Trainer_dis1.alpha = .1 self.DOE_Trainer_dis1.add_parameter("meta_model_dis1.z1", low=-10, high=10, start=5.0) self.DOE_Trainer_dis1.add_parameter("meta_model_dis1.z2", low=0, high=10, start=2.0) self.DOE_Trainer_dis1.add_parameter("meta_model_dis1.y2", low=-100, high=100) self.DOE_Trainer_dis1.add_event("meta_model_dis1.train_next") self.DOE_Trainer_dis1.workflow.add("local_opt_dis1") self.add('reset_train', Driver()) self.reset_train.add_event('meta_model_dis1.reset_training_data') self.reset_train.add_event('meta_model_dis2.reset_training_data') self.reset_train.workflow.add(['meta_model_dis1', 'meta_model_dis2']) # build workflow for bliss2000 self.add('driver', FixedPointIterator()) # self.add('main_driver', IterateUntil()) # self.main_driver.max_iterations = 1 self.driver.tolerance = .0001 # self.driver.workflow.add(['local_opt_dis1','reset_train','DOE_Trainer_dis1','DOE_Trainer_dis2','sysopt']) self.driver.workflow.add(['sysopt']) self.driver.add_parameter('x1_store', low=0, high=10.0) self.driver.add_constraint('meta_model_dis1.x1 = x1_store') self.driver.add_parameter('z1_store', low=0, high=10.0) self.driver.add_constraint('meta_model_dis1.z1 = z1_store') self.driver.add_parameter('z2_store', low=0, high=10.0) self.driver.add_constraint('meta_model_dis1.z2 = z2_store')
class Geometry(VariableTree): """Container of variables defining the mixer-ejector geometry""" length = Float(10.0, units='ft', desc='Ejector width') width = Float(6.0, units='ft', desc='Ejector width') Apri = Float(6.00, units='ft**2', desc='Primary nozzle exit area') Asec = Float(8.40, units='ft**2', desc='Secondary nozzle exit area') Aexit = Float(13.68, units='ft**2', desc='Ejector exit area') AsAp = Float(1.4,desc='Area ratio (secondary area/primary area)') AR = Float(1.25, desc='Aspect ratio of the ejector at the inlet') AeAt = Float(0.95, desc='Area ratio (exit area/total inlet area)') ChuteAngles = Float(-10.0, units='deg', desc='Chute divergence angles. Outer tangent line relative to ejector flow surface at nozzle downstream of mixer exit') Num_Lobes = Float(18.0, desc='Number of spokes or lobes of the mixer') LhMh = Float(0.90, desc='Lobe height to mixing section height (from centerline) ratio (chute penetration)') LhWave = Float(2.88, desc='Lobe height to wavelength ratio') def calc_geom(self,length,Apri,AsAp,AR,AeAt,LhMh,LhWave): self.length = length self.Apri = Apri self.AsAp = AsAp self.AR = AR self.AeAT = AeAt self.LhMh = LhMh self.LhWave = LhWave self.Asec = AsAp*Apri self.Aexit = AeAt*(Apri+self.Asec) self.width = (AR*(Apri+self.Asec))**0.5 self.Num_Lobes = 4*self.width**2*LhWave/((Apri+self.Asec)*LhMh)
class Oneinp(Component): """ A simple input component """ ratio1 = Float(1.00, iotype='in', desc='Float Variable', units='mm') # not a pressure unit ratio2 = Float(1.00, iotype='in', desc='Float Variable', units='atm') # pressure in atm ratio3 = Float(1.00, iotype='in', desc='Float Variable', units='torr') # pressure in torr ratio4 = Float(1.00, iotype='in', desc='Float Variable', units='psi') # pressure in psi ratio5 = Float(1.00, iotype='in', desc='Float Variable', units='bar') # pressure in bar ratio6 = Float(1.00, iotype='in', desc='Float variable ', units='cal/(mol*degK)') #R, Gas constant ratio7 = Float(1.00, iotype='in', desc='Float variable ', units='m') # Meter ratio8 = Float(1.00, iotype='in', desc='Float variable ', units='mm') # millimeter ratio9 = Float(1, iotype='in', desc='Float variable', units='degR') # temp in R ratio10 = Float(1, iotype='in', desc='Float variable', units='degK') # temp in K ratio11 = Float(1, iotype='in', desc='Float variable', units='dyn') # force in dyn ratio12 = Float(1, iotype='in', desc='Float variable', units='N') # force in N ratio13 = Float(1, iotype='in', desc='Float variable', units='dyn') # force in dyn ratio14 = Float(1, iotype='in', desc='Float variable', units='lb') # mass in lb ratio15 = Float(2, iotype='in', desc='Float variable') # no units defined ratio16 = Float(2, iotype='in', desc='Float variable', units='dyn') # force in dyn ratio17 = Float(1, iotype='in', desc='Float variable', units='deg') # angle in deg def __init__(self): super(Oneinp, self).__init__() def execute(self): """
class DomeStatic(NastranComponent): for i in range(1, 157): cmd = "bar%d_init_area = 1.00" % i exec(cmd) for i in range(157, 253): cmd = "tria%d_init_thickness = 1.00" % i exec(cmd) for i in range(1, 157): cmd = 'bar%d_area = Float(bar%d_init_area, nastran_card="PROD",\ nastran_id=%d, \ nastran_field="A",\ iotype="in", units="inch*inch",\ desc="Cross-sectional area for bar %d")' % (i, i, i, i) exec(cmd) for i in range(157, 253): cmd = 'tria%d_thickness = Float(tria%d_init_thickness, nastran_card="PSHELL",\ nastran_id=%d, \ nastran_field="T",\ iotype="in", units="inch*inch",\ desc="Membrane thickness for tria %d")' % (i, i, i, i) exec(cmd) # these are stresses that will be constrained for i in range(1, 157): cmd = "bar%d_stress = Float(0., iotype='out', units='lb/(inch*inch)', desc='Axial stress in element %d')" % ( i, i) exec(cmd) for i in range(157, 253): cmd = "tria%d_stress = Float(0., iotype='out', units='lb/(inch*inch)', desc='Von Mises stress in element %d')" % ( i, i) exec(cmd) def mass(op2): return op2.grid_point_weight.mass[0] weight = Float(0., nastran_func=mass, iotype='out', units='lb', desc='Weight of the structure') def execute(self): """ Simulates the analysis of a ten bar truss structure. Force, Stress, Displacement,Frequency and Weight are returned at the Ring output. """ super(DomeStatic, self).execute() # get stresses from table with header # S T R E S S E S I N R O D E L E M E N T S ( C R O D ) isubcase = 1 for i in range(len(self.op2.rodStress[isubcase].axial)): stress = calculate_stress( (self.op2.rodStress[isubcase].axial[i + 1], self.op2.rodStress[isubcase].torsion[i + 1])) cmd = "self.bar%d_stress = stress" % (i + 1) exec(cmd) # get stresses from table with header # S T R E S S E S I N T R I A N G U L A R E L E M E N T S ( T R I A 3 )" for i in range(157, 253): biggest = self.op2.plateStress[isubcase].ovmShear[i]['CEN/3'][0] cmd = "self.tria%d_stress = biggest" % i exec(cmd)
class Postprocess_Fuzzy_Outputs(Component): """ Takes in some outputs from the fuzzy systems and creates crisp values by which to find optimal solutions. Uses alpha cuts at the the given alpha_val level. """ # set up interface to the framework #inputs are outputs from systems fuzzSys_in_1 = VarTree(FuzzyMF(), iotype='in', desc='fuzzy system output') fuzzSys_in_2 = VarTree(FuzzyMF(), iotype='in', desc='fuzzy system output') fuzzSys_in_3 = VarTree(FuzzyMF(), iotype='in', desc='fuzzy system output') fuzzSys_in_4 = VarTree(FuzzyMF(), iotype='in', desc='fuzzy system output') fuzzSys_in_5 = VarTree(FuzzyMF(), iotype='in', desc='fuzzy system output') fuzzSys_in_6 = VarTree(FuzzyMF(), iotype='in', desc='fuzzy system output') fuzzSys_in_7 = VarTree(FuzzyMF(), iotype='in', desc='fuzzy system output') fuzzSys_in_8 = VarTree(FuzzyMF(), iotype='in', desc='fuzzy system output') fuzzSys_in_9 = VarTree(FuzzyMF(), iotype='in', desc='fuzzy system output') alpha_val = Float(0.7, iotype='in', desc='alpha-cut to perform range post processing at') goalVals = Dict({'sys_phi' :6.7, 'sys_FoM' :0.775, 'sys_LoD' :12.5, 'sys_etaP' :0.875, 'sys_Pin' :3500.0, 'sys_GWT' :10000, 'sys_VH' :325}, iotype='in', desc='crisp goals for each output') PLOTMODE = Int(0, iotype='in', desc='Flag for plotting, 1 for plot') printResults = Int(1, iotype='in', desc='print results each iteration?') passthrough = Int(0, iotype='in', low=0, high=1, desc='catch flag for incompatible options') incompatCount = Int(0, iotype='in', desc='count of incomatible options') runFlag_in = Int(0, iotype='in', desc='test') runFlag_out = Int(0, iotype='out', desc='test') ranges_out = Dict({}, iotype='out', desc='alpha cuts for each fuzzy input') response_1 = Float(0.0, iotype='out', desc='crisp measure 1 to perform optimization') response_1_r = Float(0.0, iotype='out', desc='range for crisp measure 1') response_1_POS = Float(0.0, iotype='out', desc='fuzzy POS measure (dominance to crisp goal)') response_2 = Float(0.0, iotype='out', desc='crisp measure 2 to perform optimization') response_2_r = Float(0.0, iotype='out', desc='range for crisp measure 2') response_2_POS = Float(0.0, iotype='out', desc='fuzzy POS measure (dominance to crisp goal)') response_3 = Float(0.0, iotype='out', desc='crisp measure 3 to perform optimization') response_3_r = Float(0.0, iotype='out', desc='range for crisp measure 3') response_3_POS = Float(0.0, iotype='out', desc='fuzzy POS measure (dominance to crisp goal)') response_4 = Float(0.0, iotype='out', desc='crisp measure 4 to perform optimization') response_4_r = Float(0.0, iotype='out', desc='range for crisp measure 4') response_4_POS = Float(0.0, iotype='out', desc='fuzzy POS measure (dominance to crisp goal)') response_5 = Float(0.0, iotype='out', desc='crisp measure 5 to perform optimization') response_5_r = Float(0.0, iotype='out', desc='range for crisp measure 5') response_5_POS = Float(0.0, iotype='out', desc='fuzzy POS measure (dominance to crisp goal)') response_6 = Float(0.0, iotype='out', desc='crisp measure 6 to perform optimization') response_6_r = Float(0.0, iotype='out', desc='range for crisp measure 6') response_6_POS = Float(0.0, iotype='out', desc='fuzzy POS measure (dominance to crisp goal)') response_7 = Float(0.0, iotype='out', desc='crisp measure 7 to perform optimization') response_7_r = Float(0.0, iotype='out', desc='range for crisp measure 7') response_7_POS = Float(0.0, iotype='out', desc='fuzzy POS measure (dominance to crisp goal)') response_8 = Float(0.0, iotype='out', desc='crisp measure 8 to perform optimization') response_8_r = Float(0.0, iotype='out', desc='range for crisp measure 8') response_8_POS = Float(0.0, iotype='out', desc='fuzzy POS measure (dominance to crisp goal)') response_9 = Float(0.0, iotype='out', desc='crisp measure 9 to perform optimization') response_9_r = Float(0.0, iotype='out', desc='range for crisp measure 9') response_9_POS = Float(0.0, iotype='out', desc='fuzzy POS measure (dominance to crisp goal)') fuzzyPOS = Float(0.0, iotype='out', desc='Fuzzy Measure for POS (product of all POS measures') def execute(self): """ Translate fuzzy inputs to crisp values to optimize system. """ inputs = [self.fuzzSys_in_1, self.fuzzSys_in_2, self.fuzzSys_in_3, self.fuzzSys_in_4, self.fuzzSys_in_5, self.fuzzSys_in_6, self.fuzzSys_in_7, self.fuzzSys_in_8, self.fuzzSys_in_9] outs = [[self.response_1][0], [self.response_2][0], self.response_3, self.response_4, self.response_5, self.response_6, self.response_7, self.response_8, self.response_9] outs_r = [self.response_1_r, self.response_2_r, self.response_3_r, self.response_4_r, self.response_5_r, self.response_6_r, self.response_7_r, self.response_8_r, self.response_9_r] if self.passthrough == 1: if self.printResults == 1: print "Incompatible combo found..." self.response_1 = 0.0 #phi self.response_1_r = 0.0 self.response_1_POS = -1.0 self.response_2 = 0.0 #FoM self.response_2_r = 0.0 self.response_2_POS = -1.0 self.response_3 = 0.0 #LoD self.response_3_r = 0.0 self.response_3_POS = -1.0 self.response_4 = 0.0 #etaP self.response_4_r = 0.0 self.response_4_POS = -1.0 self.response_5 = 0.0 #GWT self.response_5_r = 0.0 self.response_5_POS = -1.0 self.response_6 = -99999.0 #P self.response_6_r = 0.0 self.response_6_POS = 0.0 self.response_7 = 0.0 #VH self.response_7_r = 0.0 self.response_7_POS = -1.0 return None else: #get alpha cuts for crisp responses and ranges for i in range(len(inputs)): if inputs[i].mf_key <> '': if len(inputs[i].mf_dict[inputs[i].mf_key]) == 1: #crisp value self.ranges_out[inputs[i].mf_key] = [inputs[i].mf_dict[inputs[i].mf_key][0], inputs[i].mf_dict[inputs[i].mf_key][0]] elif len(inputs[i].mf_dict[inputs[i].mf_key]) == 2: #fuzzy function self.ranges_out[inputs[i].mf_key] = fuzzyOps.alpha_cut(self.alpha_val, inputs[i].mf_dict[inputs[i].mf_key]) #capture results for crisp measures if self.ranges_out[inputs[i].mf_key] <> None: y = self.ranges_out[inputs[i].mf_key] else: y = [0.0, 0.0] if inputs[i].mf_key == 'sys_phi': self.response_1 = fuzz.defuzz(inputs[i].mf_dict[inputs[i].mf_key][0],np.array(inputs[i].mf_dict[inputs[i].mf_key][1]),'centroid') self.response_1 = self.response_1 * math.exp(-self.incompatCount)**0.5 self.response_1_r = max(y) - min(y) self.response_1_POS = fuzzyOps.fuzzyPOS(inputs[i].mf_dict[inputs[i].mf_key][0],np.array(inputs[i].mf_dict[inputs[i].mf_key][1]), self.goalVals['sys_phi']) if inputs[i].mf_key == 'sys_FoM': self.response_2 = fuzz.defuzz(inputs[i].mf_dict[inputs[i].mf_key][0],np.array(inputs[i].mf_dict[inputs[i].mf_key][1]),'centroid') self.response_2 = self.response_2 * math.exp(-self.incompatCount)**0.5 self.response_2_r = max(y) - min(y) #if self.response_2 < 0.6: # self.response_2_POS = fuzzyOps.fuzzyPOS(inputs[i].mf_dict[inputs[i].mf_key][0],np.array(inputs[i].mf_dict[inputs[i].mf_key][1]), self.goalVals['sys_FoM'], direction='max', plot=True) self.response_2_POS = fuzzyOps.fuzzyPOS(inputs[i].mf_dict[inputs[i].mf_key][0],np.array(inputs[i].mf_dict[inputs[i].mf_key][1]), self.goalVals['sys_FoM']) if inputs[i].mf_key == 'sys_LoD': self.response_3 = fuzz.defuzz(inputs[i].mf_dict[inputs[i].mf_key][0],np.array(inputs[i].mf_dict[inputs[i].mf_key][1]),'centroid') self.response_2 = self.response_3 * math.exp(-self.incompatCount)**0.5 self.response_3_r = max(y) - min(y) self.response_3_POS = fuzzyOps.fuzzyPOS(inputs[i].mf_dict[inputs[i].mf_key][0],np.array(inputs[i].mf_dict[inputs[i].mf_key][1]), self.goalVals['sys_LoD']) if inputs[i].mf_key == 'sys_etaP': self.response_4 = fuzz.defuzz(inputs[i].mf_dict[inputs[i].mf_key][0],np.array(inputs[i].mf_dict[inputs[i].mf_key][1]),'centroid') self.response_4 = self.response_4 * math.exp(-self.incompatCount)**0.5 self.response_4_r = max(y) - min(y) self.response_4_POS = fuzzyOps.fuzzyPOS(inputs[i].mf_dict[inputs[i].mf_key][0],np.array(inputs[i].mf_dict[inputs[i].mf_key][1]), self.goalVals['sys_etaP']) if inputs[i].mf_key == 'sys_GWT': #invert GWT to maximize all self.response_5 = fuzz.defuzz(inputs[i].mf_dict[inputs[i].mf_key][0],np.array(inputs[i].mf_dict[inputs[i].mf_key][1]),'centroid') self.response_5 = self.response_5 * math.exp(-self.incompatCount)**0.5 self.response_5_r = max(y) - min(y) self.response_5_POS = fuzzyOps.fuzzyPOS(inputs[i].mf_dict[inputs[i].mf_key][0],np.array(inputs[i].mf_dict[inputs[i].mf_key][1]), self.goalVals['sys_GWT'], direction='min') if inputs[i].mf_key == 'sys_P': #invert GWT to maximize all self.response_6 = 0.0-fuzz.defuzz(inputs[i].mf_dict[inputs[i].mf_key][0],np.array(inputs[i].mf_dict[inputs[i].mf_key][1]),'centroid') self.response_6 = self.response_6 * math.exp(-self.incompatCount)**0.5 self.response_6_r = max(y) - min(y) self.response_6_POS = fuzzyOps.fuzzyPOS(inputs[i].mf_dict[inputs[i].mf_key][0],np.array(inputs[i].mf_dict[inputs[i].mf_key][1]), self.goalVals['sys_Pin'], direction='min') if inputs[i].mf_key == 'sys_VH': #invert GWT to maximize all self.response_7 = fuzz.defuzz(inputs[i].mf_dict[inputs[i].mf_key][0],np.array(inputs[i].mf_dict[inputs[i].mf_key][1]),'centroid') self.response_7 = self.response_7 * math.exp(-self.incompatCount)**0.5 self.response_7_r = max(y) - min(y) self.response_7_POS = fuzzyOps.fuzzyPOS(inputs[i].mf_dict[inputs[i].mf_key][0],np.array(inputs[i].mf_dict[inputs[i].mf_key][1]), self.goalVals['sys_VH']) self.fuzzyPOS = self.response_1_POS*self.response_2_POS*self.response_3_POS*self.response_4_POS*self.response_6_POS if self.printResults == 1: #print results print "Alternative:", self.passthrough, ":", print "PHI: %.1f, (%.3f)" % (self.response_1, self.response_1_POS), print " FoM: %.3f, (%.3f)" % (self.response_2, self.response_2_POS), print " L/D: %.1f, (%.3f)" % (self.response_3, self.response_3_POS), print " etaP: %.3f, (%.3f)" % (self.response_4, self.response_4_POS), print " GWT: %.0f, (%.3f)" % (self.response_5, self.response_5_POS), print " Pinst: %.0f, (%.3f)" % (self.response_6, self.response_6_POS), print " VH: %.0f, (%.3f)" % (self.response_7, self.response_7_POS), print " FPOS: %.3f" % self.fuzzyPOS #plotting for testing if self.PLOTMODE == 1: #plot results plt.figure() i=1 for r in inputs: plt.subplot(3,2,i) if r.mf_key <> '': if len(r.mf_dict[r.mf_key]) == 1: #crisp value pass#self.ranges_out[r.mf_key] = [r.mf_dict[r.mf_key][0], r.mf_dict[r.mf_key][1]] elif len(r.mf_dict[r.mf_key]) == 2: #fuzzy function plt.plot(r.mf_dict[r.mf_key][0],r.mf_dict[r.mf_key][1]) i = i + 1 plt.show()
class floris_assembly_opt_AEP(Assembly): """ Defines the connections between each Component used in the FLORIS model """ # general input variables parameters = VarTree(FLORISParameters(), iotype='in') verbose = Bool(False, iotype='in', desc='verbosity of FLORIS, False is no output') # Flow property variables air_density = Float(iotype='in', units='kg/(m*m*m)', desc='air density in free stream') # output AEP = Float(iotype='out', units='kW', desc='total windfarm AEP') def __init__(self, nTurbines, nDirections, optimize_position=False, nSamples=0, optimize_yaw=False, datasize=0, nSpeeds=False, maxiter=100): super(floris_assembly_opt_AEP, self).__init__() if nSpeeds == False: nSpeeds = nDirections self.nTurbines = nTurbines self.nSamples = nSamples self.nDirections = nDirections self.optimize_yaw = optimize_yaw self.optimize_position = optimize_position self.datasize = datasize self.nSpeeds = nSpeeds self.maxiter = maxiter # wt_layout input variables self.add( 'rotorDiameter', Array(np.zeros(nTurbines), dtype='float', iotype='in', units='m', desc='rotor diameters of all turbine')) self.add( 'axialInduction', Array(np.zeros(nTurbines), iotype='in', dtype='float', desc='axial induction of all turbines')) self.add('hubHeight', Array(np.zeros(nTurbines), dtype='float', iotype='in', units='m', \ desc='hub heights of all turbines')) # turbine properties for ccblade and pre-calculated controller self.add( 'curve_CP', Array(np.zeros(datasize), iotype='in', desc='pre-calculated CPCT')) self.add( 'curve_CT', Array(np.zeros(datasize), iotype='in', desc='pre-calculated CPCT')) self.add( 'curve_wind_speed', Array(np.zeros(datasize), iotype='in', desc='pre-calculated CPCT')) self.add('initVelocitiesTurbines', Array(np.zeros(nTurbines), iotype='in', units='m/s')) self.add( 'generator_efficiency', Array(np.zeros(nTurbines), iotype='in', dtype='float', desc='generator efficiency of all turbines')) self.add( 'turbineX', Array(np.zeros(nTurbines), iotype='in', dtype='float', desc='x positions of turbines in original ref. frame')) self.add( 'turbineY', Array(np.zeros(nTurbines), iotype='in', dtype='float', desc='y positions of turbines in original ref. frame')) if optimize_yaw: for direction in range(0, nDirections): self.add('yaw_%d' % direction, Array(np.zeros(nTurbines), iotype='in', dtype='float', \ desc='yaw of each turbine for each direction')) else: self.add('yaw', Array(np.zeros(nTurbines), iotype='in', dtype='float', \ desc='yaw of each turbine')) # windrose input variables self.add( 'windrose_directions', Array(np.zeros(nDirections), dtype='float', iotype='in', desc='windrose directions in degrees ccw from east')) self.add( 'windrose_frequencies', Array( np.ones(nDirections), dtype='float', iotype='in', desc='windrose frequencies corresponding to windrose_directions' )) if nSpeeds == 1: self.add( 'windrose_speeds', Float( iotype='in', units='m/s', desc= 'wind speeds for each direction given in windrose_directions' )) else: self.add( 'windrose_speeds', Array( np.zeros(nDirections), dtype='float', iotype='in', units='m/s', desc= 'wind speeds for each direction given in windrose_directions' )) # Explicitly size output arrays # variables added to test individual components self.add( 'turbineXw', Array( np.zeros(nTurbines), iotype='out', units='m', desc= 'X positions of turbines in the wind direction reference frame' )) self.add( 'turbineYw', Array( np.zeros(nTurbines), iotype='out', units='m', desc= 'Y positions of turbines in the wind direction reference frame' )) self.add( 'wakeCentersYT', Array(np.zeros(nTurbines), dtype='float', iotype='out', units='m', desc='centers of the wakes at each turbine')) self.add( 'wakeDiametersT', Array(np.zeros(nTurbines), dtype='float', iotype='out', units='m', desc='diameters of each of the wake zones for each of the \ wakes at each turbine')) self.add( 'wakeOverlapTRel', Array(np.zeros(nTurbines), dtype='float', iotype='out', units='m', desc='ratio of overlap area of each zone to rotor area')) # standard output self.add( 'velocitiesTurbines_directions', Array(np.zeros([nDirections, nTurbines]), iotype='out', units='m/s', dtype='float', desc='effective windspeed at each turbine \ in each direction ccw from east using direction to' )) self.add( 'wt_power_directions', Array(np.zeros([nDirections, nTurbines]), iotype='out', units='kW', dtype='float', desc='power of each turbine in each direction ccw from \ east using direction to')) self.add( 'power_directions', Array(np.zeros(nDirections), iotype='out', units='kW', desc='total windfarm power \ in each direction ccw from east using direction to' )) if nSamples > 0: # flow samples self.add( 'ws_positionX', Array(np.zeros(nSamples), iotype='in', units='m', desc='X positions of sampling points')) self.add( 'ws_positionY', Array(np.zeros(nSamples), iotype='in', units='m', desc='Y position of sampling points')) self.add( 'ws_positionZ', Array(np.zeros(nSamples), iotype='in', units='m', desc='Z position of sampling points')) for direction in range(0, nDirections): self.add( 'ws_array_%d' % direction, Array(np.zeros(nSamples), iotype='out', units='m/s', desc='predicted wind speed at sampling points')) def configure(self): # rename options nTurbines = self.nTurbines nDirections = self.nDirections optimize_position = self.optimize_position optimize_yaw = self.optimize_yaw datasize = self.datasize nSamples = self.nSamples nSpeeds = self.nSpeeds maxiter = self.maxiter # add driver so the workflow is not overwritten later if optimize_position or optimize_yaw: self.add('driver', SLSQPdriver()) # add AEP component first so it can be connected to F6 = self.add('floris_AEP', AEP(nDirections=nDirections)) F6.missing_deriv_policy = 'assume_zero' self.connect('windrose_frequencies', 'floris_AEP.windrose_frequencies') self.connect('floris_AEP.AEP', 'AEP') self.connect('floris_AEP.power_directions_out', 'power_directions') # set up constraints self.add('floris_dist_const', dist_const(nTurbines=nTurbines)) self.connect('turbineX', 'floris_dist_const.turbineX') self.connect('turbineY', 'floris_dist_const.turbineY') if nSamples > 0: samplingNonSampling = ['', 'Sampling_'] else: samplingNonSampling = [''] for i in range(0, nDirections): # add fixed point iterator self.add('FPIdriver_%d' % i, FixedPointIterator()) self.add( 'rotor_CPCT_%d' % i, CPCT_Interpolate(nTurbines=self.nTurbines, datasize=self.datasize)) CP = 'rotor_CPCT_%d.CP' % i CT = 'rotor_CPCT_%d.CT' % i CPCT = 'rotor_CPCT_%d' % i # add components of floris to assembly F2 = self.add('floris_windframe_%d' % i, floris_windframe(nTurbines=nTurbines)) F2.missing_deriv_policy = 'assume_zero' self.add('floris_wcent_wdiam_%d' % i, floris_wcent_wdiam(nTurbines=nTurbines)) F4 = self.add('floris_overlap_%d' % i, floris_overlap(nTurbines=nTurbines)) F4.missing_deriv_policy = 'assume_zero' self.add('floris_power_%d' % i, floris_power(nTurbines=nTurbines)) # add visualization components of floris to assembly if nSamples > 0: self.add( 'Sampling_floris_windframe_%d' % i, floris_windframe(nTurbines=nTurbines, nSamples=nSamples)) self.add( 'Sampling_floris_wcent_wdiam_%d' % i, floris_wcent_wdiam(nTurbines=nTurbines, nSamples=nSamples)) self.add('Sampling_floris_overlap_%d' % i, floris_overlap(nTurbines=nTurbines)) self.add('Sampling_floris_power_%d' % i, floris_power(nTurbines=nTurbines, nSamples=nSamples)) # connect inputs to components self.connect('curve_CP', 'rotor_CPCT_%d.windSpeedToCPCT.CP' % i) self.connect('curve_CT', 'rotor_CPCT_%d.windSpeedToCPCT.CT' % i) self.connect('curve_wind_speed', 'rotor_CPCT_%d.windSpeedToCPCT.wind_speed' % i) self.connect('parameters.pP', 'rotor_CPCT_%d.pP' % i) for ssn in samplingNonSampling: self.connect('parameters', [ '%sfloris_wcent_wdiam_%d.parameters' % (ssn, i), '%sfloris_power_%d.parameters' % (ssn, i) ]) self.connect('verbose', [ '%sfloris_windframe_%d.verbose' % (ssn, i), '%sfloris_wcent_wdiam_%d.verbose' % (ssn, i), '%sfloris_power_%d.verbose' % (ssn, i) ]) self.connect('turbineX', '%sfloris_windframe_%d.turbineX' % (ssn, i)) self.connect('turbineY', '%sfloris_windframe_%d.turbineY' % (ssn, i)) self.connect('rotorDiameter', [ '%sfloris_wcent_wdiam_%d.rotorDiameter' % (ssn, i), '%sfloris_overlap_%d.rotorDiameter' % (ssn, i), '%sfloris_power_%d.rotorDiameter' % (ssn, i) ]) self.connect('axialInduction', '%sfloris_power_%d.axialInduction' % (ssn, i)) self.connect( 'generator_efficiency', '%sfloris_power_%d.generator_efficiency' % (ssn, i)) if nSamples > 0: # connections needed for visualization self.connect('ws_positionX', 'Sampling_floris_windframe_%d.ws_positionX' % i) self.connect('ws_positionY', 'Sampling_floris_windframe_%d.ws_positionY' % i) self.connect('ws_positionZ', 'Sampling_floris_windframe_%d.ws_positionZ' % i) self.connect('hubHeight', 'Sampling_floris_wcent_wdiam_%d.hubHeight' % i) if optimize_yaw: yawToConnect = 'yaw_%d' % i else: yawToConnect = 'yaw' self.connect(yawToConnect, '%s.yaw' % CPCT) for ssn in samplingNonSampling: self.connect(yawToConnect, [ '%sfloris_wcent_wdiam_%d.yaw' % (ssn, i), '%sfloris_power_%d.yaw' % (ssn, i) ]) for ssn in samplingNonSampling: self.connect('air_density', '%sfloris_power_%d.air_density' % (ssn, i)) self.connect('windrose_directions[%d]' % i, '%sfloris_windframe_%d.wind_direction' % (ssn, i)) # for satisfying the verbosity in windframe for ssn in samplingNonSampling: self.connect(CT, '%sfloris_windframe_%d.Ct' % (ssn, i)) self.connect(CP, '%sfloris_windframe_%d.Cp' % (ssn, i)) self.connect(yawToConnect, '%sfloris_windframe_%d.yaw' % (ssn, i)) self.connect('axialInduction', '%sfloris_windframe_%d.axialInduction' % (ssn, i)) # ############### Connections between components ################## # connections from CtCp calculation to other components for ssn in samplingNonSampling: self.connect(CT, [ '%sfloris_wcent_wdiam_%d.Ct' % (ssn, i), '%sfloris_power_%d.Ct' % (ssn, i) ]) self.connect(CP, '%sfloris_power_%d.Cp' % (ssn, i)) # connections from floris_windframe to floris_wcent_wdiam self.connect('%sfloris_windframe_%d.turbineXw' % (ssn, i), '%sfloris_wcent_wdiam_%d.turbineXw' % (ssn, i)) self.connect('%sfloris_windframe_%d.turbineYw' % (ssn, i), '%sfloris_wcent_wdiam_%d.turbineYw' % (ssn, i)) # connections from floris_wcent_wdiam to floris_overlap self.connect( '%sfloris_wcent_wdiam_%d.wakeCentersYT' % (ssn, i), '%sfloris_overlap_%d.wakeCentersYT' % (ssn, i)) self.connect( '%sfloris_wcent_wdiam_%d.wakeDiametersT' % (ssn, i), '%sfloris_overlap_%d.wakeDiametersT' % (ssn, i)) # connections from floris_windframe to floris_overlap self.connect('%sfloris_windframe_%d.turbineXw' % (ssn, i), '%sfloris_overlap_%d.turbineXw' % (ssn, i)) self.connect('%sfloris_windframe_%d.turbineYw' % (ssn, i), '%sfloris_overlap_%d.turbineYw' % (ssn, i)) # connections from floris_windframe to floris_power self.connect('%sfloris_windframe_%d.turbineXw' % (ssn, i), '%sfloris_power_%d.turbineXw' % (ssn, i)) # connections from floris_overlap to floris_power self.connect('%sfloris_overlap_%d.wakeOverlapTRel' % (ssn, i), '%sfloris_power_%d.wakeOverlapTRel' % (ssn, i)) # additional connections needed for visualization if nSamples > 0: self.connect('Sampling_floris_windframe_%d.wsw_position' % i, [ 'Sampling_floris_wcent_wdiam_%d.wsw_position' % i, 'Sampling_floris_power_%d.wsw_position' % i ]) self.connect('Sampling_floris_wcent_wdiam_%d.wakeCentersY' % i, 'Sampling_floris_power_%d.wakeCentersY' % i) self.connect('Sampling_floris_wcent_wdiam_%d.wakeCentersZ' % i, 'Sampling_floris_power_%d.wakeCentersZ' % i) self.connect( 'Sampling_floris_wcent_wdiam_%d.wakeDiameters' % i, 'Sampling_floris_power_%d.wakeDiameters' % i) self.connect('Sampling_floris_power_%d.ws_array' % i, 'ws_array_%d' % i) # connections from floris_power to floris_AEP self.connect('floris_power_%d.power' % i, 'floris_AEP.power_directions[%d]' % i) # ################################################################# # add to workflow exec( "self.FPIdriver_%d.workflow.add(['rotor_CPCT_%d', 'floris_windframe_%d', \ 'floris_wcent_wdiam_%d', 'floris_overlap_%d', 'floris_power_%d'])" % (i, i, i, i, i, i)) exec( "self.FPIdriver_%d.add_parameter('rotor_CPCT_%d.wind_speed_hub', low=0., high=100.)" % (i, i)) exec( "self.FPIdriver_%d.add_constraint('rotor_CPCT_%d.wind_speed_hub = \ floris_power_%d.velocitiesTurbines')" % (i, i, i)) self.driver.workflow.add('FPIdriver_%d' % i) if nSamples > 0: self.driver.workflow.add([ 'Sampling_floris_windframe_%d' % i, 'Sampling_floris_wcent_wdiam_%d' % i, 'Sampling_floris_overlap_%d' % i, 'Sampling_floris_power_%d' % i ]) if nSpeeds > 1: for i in range(0, nSpeeds): for ssn in samplingNonSampling: self.connect('windrose_speeds[%d]' % i, '%sfloris_power_%d.wind_speed' % (ssn, i)) self.connect('windrose_speeds[%d]' % i, '%sfloris_windframe_%d.wind_speed' % (ssn, i)) else: for i in range(0, nDirections): for ssn in samplingNonSampling: self.connect('windrose_speeds', '%sfloris_power_%d.wind_speed' % (ssn, i)) self.connect('windrose_speeds', '%sfloris_windframe_%d.wind_speed' % (ssn, i)) # add AEP calculations to workflow self.driver.workflow.add(['floris_AEP', 'floris_dist_const']) if optimize_position or optimize_yaw: # set up driver self.driver.iprint = 3 self.driver.accuracy = 1.0e-12 self.driver.maxiter = maxiter self.driver.add_objective('-floris_AEP.AEP') if optimize_position: self.driver.add_parameter('turbineX', low=7 * 126.4, high=np.sqrt(self.nTurbines) * 7 * 126.4) self.driver.add_parameter('turbineY', low=7 * 126.4, high=np.sqrt(self.nTurbines) * 7 * 126.4) self.driver.add_constraint( 'floris_dist_const.separation > 2*rotorDiameter[0]') if optimize_yaw: for direction in range(0, self.nDirections): self.driver.add_parameter('yaw_%d' % direction, low=-30., high=30., scaler=1.)
class DumbVT3(VariableTree): a = Float(1., units='ft') b = Float(12., units='inch')
class LogisticRegression(HasTraits): implements(ISurrogate) alpha = Float(.1, low=0, iotype='in', desc='L2 regularization strength') def __init__(self, X=None, Y=None, alpha=.1): # must call HasTraits init to set up Traits stuff super(LogisticRegression, self).__init__() self.m = None #number of independents self.n = None #number of training points self.alpha = alpha self.degenerate = False if X is not None and Y is not None: self.train(X, Y) def lik(self, betas): """ Likelihood of the data under the current settings of parameters. """ # Data likelihood l = 0 for i in range(self.n): l += log(sigmoid(self.Y[i] * \ np.dot(betas, self.X[i,:]))) # Prior likelihood for k in range(1, self.X.shape[1]): l -= (self.alpha / 2.0) * self.betas[k]**2 #multiply by -1 so the optimizer will maxize return -1 * l def get_uncertain_value(self, value): """Returns the value iself. Logistic regressions don't have uncertainty.""" return value def train(self, X, Y): """ Define the gradient and hand it off to a scipy gradient-based optimizer. """ #normalize all Y data to be between -1 and 1 low = min(Y) high = max(Y) #there was no data to predict on, so just degenerate to predicting True all the time self.degenerate = False if high == low: self.degenerate = high return self.m = 2.0 / (high - low) self.b = (2.0 * low / (low - high)) - 1 #constants for unscaling the output self.z = high - low self.w = low self.X = np.array(X) self.Y = self.m * np.array(Y) + self.b self.n = len(X) self.betas = np.zeros(len(X[0])) # Define the derivative of the likelihood with respect to beta_k. # Need to multiply by -1 because we will be minimizing. dB_k = lambda B, k : (k > 0) * self.alpha * B[k] - np.sum([ \ self.Y[i] * self.X[i, k] * \ sigmoid(-self.Y[i] *\ np.dot(B, self.X[i,:])) \ for i in range(self.n)]) # The full gradient is just an array of componentwise derivatives dB = lambda B : np.array([dB_k(B, k) \ for k in range(self.X.shape[1])]) # Optimize self.betas = fmin_bfgs(self.lik, self.betas, fprime=dB, disp=False) def predict(self, new_x): """Calculates a predicted value of the response based on the current trained model for the supplied list of inputs. """ if self.degenerate: return self.degenerate return self.z * sigmoid(np.dot(self.betas, np.array(new_x))) + self.w
class EGO(Architecture): initial_DOE_size = Int(10, iotype="in", desc="Number of initial training points to use.") sample_iterations = Int(10, iotype="in", desc="Number of adaptively sampled points to use.") EI_PI = Enum( "PI", values=["EI", "PI"], iotype="in", desc="Switch to decide between EI or PI for infill criterion.") min_ei_pi = Float( 0.001, iotype="in", desc="EI or PI to use for stopping condition of optimization.") def __init__(self, *args, **kwargs): super(EGO, self).__init__(*args, **kwargs) # the following variables determine the behavior of check_config self.param_types = ['continuous'] self.num_allowed_objectives = 1 self.has_coupling_vars = False def configure(self): self._tdir = mkdtemp() self.comp_name = None #check to make sure no more than one component is being referenced compnames = set() for param in self.parent.get_parameters().values(): compnames.update(param.get_referenced_compnames()) if len(compnames) > 1: self.parent.raise_exception( 'The EGO architecture can only be used on one' 'component at a time, but parameters from %s ' 'were added to the problem formulation.' % compnames, ValueError) self.comp_name = compnames.pop() #change name of component to add '_model' to it. # lets me name the metamodel as the old name self.comp = getattr(self.parent, self.comp_name) self.comp.name = "%s_model" % self.comp_name #add in the metamodel meta_model = self.parent.add( self.comp_name, MetaModel()) #metamodel now replaces old component with same name meta_model.default_surrogate = KrigingSurrogate() meta_model.model = self.comp meta_model_recorder = DBCaseRecorder( os.path.join(self._tdir, 'trainer.db')) meta_model.recorder = meta_model_recorder meta_model.force_execute = True EI = self.parent.add("EI", ExpectedImprovement()) self.objective = self.parent.get_objectives().keys()[0] EI.criteria = self.objective pfilter = self.parent.add("filter", ParetoFilter()) pfilter.criteria = [self.objective] pfilter.case_sets = [ meta_model_recorder.get_iterator(), ] pfilter.force_execute = True #Driver Configuration DOE_trainer = self.parent.add("DOE_trainer", DOEdriver()) DOE_trainer.sequential = True DOE_trainer.DOEgenerator = OptLatinHypercube( num_samples=self.initial_DOE_size) for name, param in self.parent.get_parameters().iteritems(): DOE_trainer.add_parameter(param) DOE_trainer.add_event("%s.train_next" % self.comp_name) DOE_trainer.case_outputs = [self.objective] DOE_trainer.recorders = [DBCaseRecorder(':memory:')] EI_opt = self.parent.add("EI_opt", Genetic()) EI_opt.opt_type = "maximize" EI_opt.population_size = 100 EI_opt.generations = 10 #EI_opt.selection_method = "tournament" for name, param in self.parent.get_parameters().iteritems(): EI_opt.add_parameter(param) EI_opt.add_objective("EI.%s" % self.EI_PI) retrain = self.parent.add("retrain", Driver()) retrain.recorders = self.data_recorders retrain.add_event("%s.train_next" % self.comp_name) iter = self.parent.add("iter", IterateUntil()) iter.max_iterations = self.sample_iterations iter.add_stop_condition('EI.PI <= %s' % self.min_ei_pi) #Data Connections self.parent.connect("filter.pareto_set", "EI.best_case") self.parent.connect(self.objective, "EI.predicted_value") #Iteration Heirarchy self.parent.driver.workflow.add(['DOE_trainer', 'iter']) #DOE_trainer.workflow.add(self.comp_name) iter.workflow = SequentialWorkflow() iter.workflow.add(['filter', 'EI_opt', 'retrain']) #EI_opt.workflow.add([self.comp_name,'EI']) retrain.workflow.add(self.comp_name) def cleanup(self): shutil.rmtree(self._tdir, ignore_errors=True)
class NEWSUMTdriver(DriverUsesDerivatives): """ Driver wrapper of Fortran version of NEWSUMT. .. todo:: Check to see if this itmax variable is needed. NEWSUMT might handle it for us. """ implements(IHasParameters, IHasIneqConstraints, IHasObjective, IOptimizer) itmax = Int(10, iotype='in', desc='Maximum number of iterations before \ termination.') default_fd_stepsize = Float(0.01, iotype='in', desc='Default finite ' \ 'difference stepsize. Parameters with ' \ 'specified values override this.') ilin = Array(dtype=numpy_int, default_value=zeros(0, 'i4'), iotype='in', desc='Array designating whether each constraint is linear.') # Control parameters for NEWSUMT. # NEWSUMT has quite a few parameters to give the user control over aspects # of the solution. epsgsn = Float(0.001, iotype='in', desc='Convergence criteria \ of the golden section algorithm used for the \ one dimensional minimization.') epsodm = Float(0.001, iotype='in', desc='Convergence criteria \ of the unconstrained minimization.') epsrsf = Float(0.001, iotype='in', desc='Convergence criteria \ for the overall process.') g0 = Float(0.1, iotype='in', desc='Initial value of the transition \ parameter.') ra = Float(1.0, iotype='in', desc='Penalty multiplier. Required if mflag=1') racut = Float(0.1, iotype='in', desc='Penalty multiplier decrease ratio. \ Required if mflag=1.') ramin = Float(1.0e-13, iotype='in', desc='Lower bound of \ penalty multiplier. \ Required if mflag=1.') stepmx = Float(2.0, iotype='in', desc='Maximum bound imposed on the \ initial step size of the one-dimensional \ minimization.') iprint = Int(0, iotype='in', desc='Print information during NEWSUMT \ solution. Higher values are more verbose. If 0,\ print initial and final designs only.', high=4, low=0) lobj = Int(0, iotype='in', desc='Set to 1 if linear objective function.') maxgsn = Int(20, iotype='in', desc='Maximum allowable number of golden \ section iterations used for 1D minimization.') maxodm = Int(6, iotype='in', desc='Maximum allowable number of one \ dimensional minimizations.') maxrsf = Int(15, iotype='in', desc='Maximum allowable number of \ unconstrained minimizations.') mflag = Int(0, iotype='in', desc='Flag for penalty multiplier. \ If 0, initial value computed by NEWSUMT. \ If 1, initial value set by ra.') def __init__(self, *args, **kwargs): super(NEWSUMTdriver, self).__init__(*args, **kwargs) self.iter_count = 0 # Save data from common blocks into the driver self.contrl = _contrl() self.countr = _countr() # define the NEWSUMTdriver's private variables # note, these are all resized in config_newsumt # basic stuff self.design_vals = zeros(0, 'd') self.constraint_vals = [] # temp storage self.__design_vals_tmp = zeros(0, 'd') self._ddobj = zeros(0) self._dg = zeros(0) self._dh = zeros(0) self._dobj = zeros(0) self._g = zeros(0) self._gb = zeros(0) self._g1 = zeros(0) self._g2 = zeros(0) self._g3 = zeros(0) self._s = zeros(0) self._sn = zeros(0) self._x = zeros(0) self._iik = zeros(0, dtype=int) self._lower_bounds = zeros(0) self._upper_bounds = zeros(0) self._iside = zeros(0) self.fdcv = zeros(0) # Just defined here. Set elsewhere self.n1 = self.n2 = self.n3 = self.n4 = 0 # Ready inputs for NEWSUMT self._obj = 0.0 self._objmin = 0.0 self.isdone = False self.resume = False self.uses_Hessians = False def start_iteration(self): """Perform the optimization.""" # Flag used to figure out if we are starting a new finite difference self.baseline_point = True # set newsumt array sizes and more... self._config_newsumt() self.iter_count = 0 # get the values of the parameters # check if any min/max constraints are violated by initial values for i, val in enumerate(self.get_parameters().values()): value = val.evaluate(self.parent) self.design_vals[i] = value # next line is specific to NEWSUMT self.__design_vals_tmp[i] = value # Call the interruptible version of SUMT in a loop that we manage self.isdone = False self.resume = False def continue_iteration(self): """Returns True if iteration should continue.""" return not self.isdone and self.iter_count < self.itmax def pre_iteration(self): """Checks or RunStopped and evaluates objective.""" super(NEWSUMTdriver, self).pre_iteration() if self._stop: self.raise_exception('Stop requested', RunStopped) def run_iteration(self): """ The NEWSUMT driver iteration.""" self._load_common_blocks() try: ( fmin, self._obj, self._objmin, self.design_vals, self.__design_vals_tmp, self.isdone, self.resume) = \ newsumtinterruptible.newsuminterruptible(user_function, self._lower_bounds, self._upper_bounds, self._ddobj, self._dg, self._dh, self._dobj, self.fdcv, self._g, self._gb, self._g1, self._g2, self._g3, self._obj, self._objmin, self._s, self._sn, self.design_vals, self.__design_vals_tmp, self._iik, self.ilin, self._iside, self.n1, self.n2, self.n3, self.n4, self.isdone, self.resume, analys_extra_args = (self,)) except Exception, err: self._logger.error(str(err)) raise self._save_common_blocks() self.iter_count += 1 # Update the parameters and run one final time with what it gave us. # This update is needed because I obeserved that the last callback to # user_function is the final leg of a finite difference, so the model # is not in sync with the final design variables. if not self.continue_iteration(): dvals = [float(val) for val in self.design_vals] self.set_parameters(dvals) super(NEWSUMTdriver, self).run_iteration() self.record_case()
class Something(VariableTree): data = Float(10.0)
class Datain(Container): # def __init__(self,name): # Container.__init__(self, name) # """ namelist 'DATAIN' for AXOD. """ ttin = Float(iotype='in', units='degR', desc='Inlet total temperature (radially constant).') ptin = Float(iotype='in', units='psi', desc='Inlet total pressure (radially constant).') pfind = Float(iotype='in', desc='Turbine total pressure ratio to be searched for') rpm = Float(iotype='in', units=('1/min'), desc='Stage rotative speed.') #seta = Float(iotype='in', desc='Stator efficiency, decimal.') seta = Array(_ZEROS5,dtype=float32,shape=(5,),iotype='in') #scf = Float(iotype='in', desc='Stator flow coefficient, decimal.') scf = Array(_ZEROS5,dtype=float32,shape=(5,),iotype='in') #reta = Float(iotype='in', desc='Rotor efficiency, decimal.') reta = Array(_ZEROS5,dtype=float32,shape=(5,),iotype='in') #rcf = Float(iotype='in', desc='Rotor flow coefficient, decimal.') rcf = Array(_ZEROS5,dtype=float32,shape=(5,),iotype='in') #ttinh = Float(iotype='in', units= 'degR', \ # desc='Inlet total temperature radial distribution') ttinh = Array(_ZEROS5,dtype=float32,shape=(5,),iotype='in') #ptinh = Float(iotype='in', units= 'psi', # desc='Inlet total pressure distribution') ptinh = Array(_ZEROS5,dtype=float32,shape=(5,),iotype='in') #alf0h = Float(iotype='in', units= 'deg', # desc='Inlet flow angle radial distribution') alf0h = Array(_ZEROS5,dtype=float32,shape=(5,),iotype='in') wair = Float(iotype='in', desc='Inlet water/air ratio') fair = Float(iotype='in', desc='Inlet fuel/air ratio') ptps = Float(iotype='in', desc='Starting value of first-stator meanline Inlet total to exit-static pressure ratio') delc = Float(iotype='in', desc='ptps increment to initial blade-row choke') dell = Float(iotype='in', desc='ptps increment from initial to last blade-row choke') dela = Float(iotype='in', desc='ptps increment from last blade-row choke to exit-annulus choke') stg = Float(iotype='in', desc='Number of stages, max 8') sect = Float(iotype='in', desc='Number of radial sectors, max 6') expn = Float(iotype='in', desc='Negative-incidence exponent, default=4.0') rg = Float(iotype='in', units='(ft*lbf)/(lbm*degR)',desc='Gas constant') paf = Float(iotype='in',desc='Profile (temp & press) averaging switch for next stage inlet') sli = Float(iotype='in',desc='Stage loss-value for srec, seta, scf, rrec, reta, rcf, rtf') aacs = Float(iotype='in',desc='Turbine-exit mach number for termination of speed line') vctd = Float(iotype='in',desc='Output Switch (1.0-overall performance plus all variable values)') #pcnh = Float(iotype='in',desc='Sector height distribution, fraction of annulus height') pcnh = Array(_ZEROS5,dtype=float32,shape=(5,),iotype='in') wg = Float(iotype='in',units='lb/s',desc='Mass flow rate') epr = Float(iotype='in',desc='switch for high pressure-ratio correction to blade row efficiency') wtol = Float(iotype='in',desc='Tolerance for mass-flow rate convergence, default=1.0e-5') rhotol = Float(iotype='in',desc='Tolerance for density convergence, default=1.0e-4') prtol = Float(iotype='in',desc='Tolerance for presuure ratio convergenc, default=1.0e-8') trloop = Float(iotype='in',desc='Debug output switch for iteration control variables') pfind = Float(iotype='in',desc='Selected value of turbine total pressure to be searched for') dhfind = Float(iotype='in',desc='Selected value of turbine specific work to be searched for') iar = Int(iotype='in',desc='Switch for axial chord length, default=0') icyl = Int(iotype='in',desc='Switch for blading angle definition,default=0') icf = Int(iotype='in',desc='Switch for flow coefficient variation, default=0') endplt = Float(iotype='in',desc='Switch for writing a map file in NEPP format,default=0') endjob = Float(iotype='in',desc='Switch for last case, default=0') stage = Float(iotype='in',desc='Stage Number') #gamg = Float(iotype='in',desc='Specific heat ratio') gamg = Array(_ZEROS5,dtype=float32,shape=(5,),iotype='in') #dr = Float(iotype='in',units='inch',desc='Hub diameter') dr = Array(_ZEROS5,dtype=float32,shape=(5,),iotype='in') #dt = Float(iotype='in',units='inch',desc='Tip diameter') dt = Array(_ZEROS5,dtype=float32,shape=(5,),iotype='in') #rwg = Float(iotype='in',desc='Ratio of Station mass-flow rate to turbine inlet mass-flow rate') rwg = Array(_ZEROS5,dtype=float32,shape=(5,),iotype='in') #twg = Float(iotype='in',units='degR',desc='Temperature of the Cooolant specified by rwg') twg = Array(_ZEROS5,dtype=float32,shape=(5,),iotype='in') #pwg = Float(iotype='in',units='psi',desc='Pressure of the Cooolant specified by pwg') pwg = Array(_ZEROS5,dtype=float32,shape=(5,),iotype='in') #sdia = Float(iotype='in',units='deg',desc='Stator vane inlet angle') sdia = Array(_ZEROS5,dtype=float32,shape=(5,),iotype='in') #sdea = Float(iotype='in',units='deg',desc='Stator vane exit angle') sdea = Array(_ZEROS5,dtype=float32,shape=(5,),iotype='in') #spa = Float(iotype='in',units='inch**2',desc='Stator throat area per unit height') spa = Array(_ZEROS5,dtype=float32,shape=(5,),iotype='in') sesth = Float(iotype='in',desc='Ratio of blade height at stator exit to blade height at stator throat') #rdia = Float(iotype='in',units='deg',desc='Rotor blade inlet angle') rdia = Array(_ZEROS5,dtype=float32,shape=(5,),iotype='in') #rdea = Float(iotype='in',units='deg',desc='Rotor blade exit angle') rdea = Array(_ZEROS5,dtype=float32,shape=(5,),iotype='in') #rpa = Float(iotype='in',units='inch**2',desc='Rotor throat area per unit height') rpa = Array(_ZEROS5,dtype=float32,shape=(5,),iotype='in') rerth = Float(iotype='in',desc='Ratio of blade height at rotor exit to blade height at rotor throat') #srec = Float(iotype='in',desc='Stator inlet recovery efficiency, decimal') srec = Array(_ZEROS5,dtype=float32,shape=(5,),iotype='in') #rrec = Float(iotype='in',desc='Rotor inlet recovery efficiency, decimal') rrec = Array(_ZEROS5,dtype=float32,shape=(5,),iotype='in') #rtf = Float(iotype='in',desc='Rotor test factor, decimal') rtf = Array(_ZEROS5,dtype=float32,shape=(5,),iotype='in') #rvu1 = Float(iotype='in',units='inch*ft/s',desc='Design Stator-exit angular momentum') rvu1 = Array(_ZEROS5,dtype=float32,shape=(5,),iotype='in') #rvu2 = Float(iotype='in',units='inch*ft/s',desc='Design rotor-exit angular momentum') rvu2 = Array(_ZEROS5,dtype=float32,shape=(5,),iotype='in') endstg = Float(iotype='in',desc='Switch for last stage, 1.0=last stage') expp = Float(iotype='in',desc='positive-incidence exponent def=3.0 ') def __init__(self): super(Datain, self).__init__() self._inputs = ['ttin', 'ptin', 'pfind', 'rpm', 'seta', 'scf', 'reta', 'rcf', \ 'ttinh','ptinh','alf0h','wair','fair','ptps','delc','dell','dela', \ 'stg','sect','expn','expp','rg','paf','sli','aacs','vctd','epr', \ 'wtol','rhotol','prtol','trloop','pfind','dhfind','iar','icyl', \ 'icf','endplt','endjob','pwg','spa','sesth','trdiag',\ 'rpa','rerth','rvu1','rvu2','endstg','stage','rdia', \ 'pcnh','gamg','sdia','srec','rtf','rrec','rwg','twg','sdea','rdea', 'wg','dr','dt'] self.ind = 0 self._nml_modified = [] self.on_trait_change(self._trait_change, '+iotype') def _trait_change(self, obj, name, old, new): """ Track *changes* so we don't output more than intended. This will *not* get called when the value is set but not changed. """ if name not in self._nml_modified: self._nml_modified.append(name) def read(self,stream): # reads the namelist datain.................. #print self._inputs # for name in self._inputs: self._nml_modified = [] line = stream.readline().strip() while line: #print 'line=',line if '/' in line: return True if '&END' in line: return True if '$END' in line: return True #print 'line=',line,' before = in line' fields = line.split('=') name0 = fields[0].strip().lower() for name in self._inputs: if name == name0 : if name not in self._nml_modified: self._nml_modified.append(name) value0 = fields[-1] #print "'%s' found in '%s'" % (name0, value0) val_field = value0.split(',') #print 'fields in val_field =', len(val_field) if len(val_field) > 2: i = 1 while i < len(val_field): #print 'name0=',name0,' val_field[',i-1,']=',val_field[i-1] if ('*' in val_field[i-1]): fld = val_field[i-1].split('*') ndi = int(fld[0]) #print ' ndi =',ndi id = 1 while id < ndi: val = float(fld[1]) #print 'self.set', name, val, i-1 self.set(name,val,[i-1]) #print ' val = ',val,' in * part' value = float(val) #print ' value[',i,'] = ',value,' in * part' id = id + 1 i = i + 1 else: #print ' after else ******* 1' val = float(val_field[i-1]) #print 'self.set', name, val, i-1 self.set(name,val,[i-1]) #name0[i] = name value = float(val) #print ' value[',i-1,'] = ',value,' in else part' #print 'name =',name,' value=',value i = i + 1 #print ' i =',i,' end of if ...' else: #print ' after else ******* 2' #val = value0.replace(',','') val = val_field[0] #print ' name=',name,' val =',val,' after array........' if ('*' in val): fld = val.split('*') nfld = int(fld[0]) val1 = float(fld[-1]) value = float(val1) #print 'name=',name,' value= ',value,' for * variable' ii = 0 while ii < nfld: self.set(name,value,[ii]) ii = ii + 1 else: #print ' name=',name,' val =',val,' befoe attrval........' attrval = getattr(self,name) if isinstance(attrval,int): #print 'name =',name,' val =',val value = int(val) setattr(self, name, value) else: value = float(val) setattr(self, name, value) # parse the value and then setattr(self, name, value) #print ' reading a new line******************' line = stream.readline().strip() # if ('/' in line) or ('&END' in line) or ('$END'in line) : return return False def write(self,stream): # reads the namelist datain.................. #print 'in write .... datain ....' stream.write(' &DATAIN\n') for name in self._nml_modified: #print 'name =', name value = getattr(self, name) if isinstance(value, ndarray): stream.write(' %s = ' % name.upper()) for val in value: stream.write('%s,' % val) stream.write('\n') else: stream.write(' %s = %s,\n' % (name.upper(), value)) stream.write(' /\n') return
class Vis3DObject(Container): """ Non-root object of 3D visualization model. """ colorby_palette = Str() symmetry = Str() symmetry_axis = Str() symmetry_angle = Float(low=0, exclude_low=True, high=180) symmetry_instances = Int(1, low=1) visible = Bool(True) def __init__(self): super(Vis3DObject, self).__init__() self._vis_name = None @property def vis_name(self): """ Returns name in visualization hierarchy. """ if not self._vis_name: name = self.get_pathname() parent = self.parent while parent and not isinstance(parent, Vis3D): parent = parent.parent if parent is None: return self.name else: pname = parent.get_pathname() if pname: self._vis_name = name[len(pname)+1:] else: self._vis_name = name return self._vis_name def clone(self, offset): """ Return a copy of ourselves, adjusting for block `offset`. """ obj = copy.copy(self) # Must be shallow! obj.parent = None obj._vis_name = None return obj def write_ensight(self, stream): """ Writes Ensight commands to `stream`. """ if not self.visible: stream.write(""" # Make invisible. part: select_byname_begin "%(name)s" part: select_byname_end part: modify_begin part: visible OFF part: modify_end """ % {'name':self.vis_name}) if self.symmetry == 'rotational': stream.write(""" # Rotational symmetry. part: select_byname_begin "%(name)s" part: select_byname_end part: modify_begin part: symmetry_type rotational part: symmetry_axis %(axis)s part: symmetry_angle %(angle)g part: symmetry_rinstances %(instances)d part: modify_end """ % {'name':self.vis_name, 'axis':self.symmetry_axis, 'angle':self.symmetry_angle, 'instances':self.symmetry_instances}) if self.colorby_palette: stream.write(""" # Color palette. part: select_byname_begin "%(name)s" part: select_byname_end part: modify_begin part: colorby_palette %(palette)s part: modify_end """ % {'name':self.vis_name, 'palette':self.colorby_palette})
def test_find_edges(self): # Verifies that we don't chain derivatives for inputs that are # connected in a parent assembly, but are not germain to our subassy # derivative. self.top = set_as_top(Assembly()) exp1 = ['y1 = 2.0*x1**2', 'y2 = 3.0*x1'] deriv1 = ['dy1_dx1 = 4.0*x1', 'dy2_dx1 = 3.0'] exp2 = ['y1 = 0.5*x1'] deriv2 = ['dy1_dx1 = 0.5'] exp3 = ['y1 = 3.5*x1'] deriv3 = ['dy1_dx1 = 3.5'] exp4 = ['y1 = x1 + 2.0*x2', 'y2 = 3.0*x1', 'y3 = x1*x2'] deriv4 = [ 'dy1_dx1 = 1.0', 'dy1_dx2 = 2.0', 'dy2_dx1 = 3.0', 'dy2_dx2 = 0.0', 'dy3_dx1 = x2', 'dy3_dx2 = x1' ] exp5 = ['y1 = x1 + 3.0*x2 + 2.0*x3'] deriv5 = ['dy1_dx1 = 1.0', 'dy1_dx2 = 3.0', 'dy1_dx3 = 2.0'] self.top.add('nest1', Assembly()) self.top.add('comp1', ExecCompWithDerivatives(exp1, deriv1)) self.top.nest1.add('driver', Driv()) self.top.nest1.add('comp2', ExecCompWithDerivatives(exp2, deriv2)) self.top.nest1.add('comp3', ExecCompWithDerivatives(exp3, deriv3)) self.top.nest1.add('comp4', ExecCompWithDerivatives(exp4, deriv4)) self.top.add('comp5', ExecCompWithDerivatives(exp5, deriv5)) self.top.driver.workflow.add(['comp1', 'nest1', 'comp5']) self.top.nest1.driver.workflow.add(['comp2', 'comp3', 'comp4']) self.top.nest1.driver.differentiator = ChainRule() obj = 'comp4.y1' con = 'comp3.y1-comp3.y1 > 0' self.top.nest1.driver.add_parameter('comp2.x1', low=-50., high=50., fd_step=.0001) self.top.nest1.driver.add_objective(obj) self.top.nest1.driver.add_constraint(con) self.top.nest1.add('real_c3_x1', Float(iotype='in', desc='I am really here')) self.top.nest1.add('real_c4_y2', Float(iotype='out', desc='I am really here')) self.top.connect('comp1.y1', 'nest1.comp2.x1') #self.top.connect('comp1.y1', 'nest1.comp2.x1') self.top.connect('comp1.y2', 'nest1.real_c3_x1') self.top.nest1.connect('real_c3_x1', 'comp3.x1') self.top.nest1.connect('comp2.y1', 'comp4.x1') self.top.nest1.connect('comp3.y1', 'comp4.x2') self.top.nest1.connect('comp4.y2', 'real_c4_y2') self.top.connect('nest1.real_c4_y2', 'comp5.x2') self.top.connect('nest1.comp4.y1', 'comp5.x1') self.top.connect('nest1.comp4.y3', 'comp5.x3') #self.top.connect('nest1.comp4.y2 + 1.0*nest1.comp4.y3', 'comp5.x3') self.top.comp1.x1 = 2.0 self.top.run() self.top.nest1.driver.differentiator.calc_gradient() edge_dict = self.top.nest1.driver.differentiator.edge_dicts[ 'nest1.driver'] self.assertTrue('x1' in edge_dict['comp2'][0]) self.assertTrue('x1' not in edge_dict['comp3'][0]) self.assertTrue('y1' in edge_dict['comp4'][1]) self.assertTrue('y2' not in edge_dict['comp4'][1])
class DREA(ExternalCode): """OpenMDAO component wrapper for DREA.""" # Variables from MEflows and Geometry variable trees # ------------------------- flow_in = VarTree(MEflows(), iotype='in') flow_out = VarTree(MEflows(), iotype='out') geo_in = VarTree(Geometry(), iotype='in') geo_out = VarTree(Geometry(), iotype='out') # NOTE: All commented out variables below are now found in the variable # trees listed above. #mode parameter used to replace ist and ifab in control.in # ------------------------- mode = Enum("Auto", ["Auto", "Fabri", "Subsonic"], iotype='in', desc='Auto mode: try Fabri choke solution, if failed, try subsonic solution.' 'Fabri mode: Fabri choke solution only, Subsonic mode: Subsonic solution only') # Variables for control.in # ------------------------- icnvl = Enum(0, [0, 1], iotype='in', desc='Control variable; 0=inviscid and viscous mixing solutions, 1=inviscid (control volume) only') ieject = Enum(1, [0, 1], iotype='in', desc='Control variable; 0=mixer solution, 1=ejector solution') #ist = Enum(1, [0, 1], iotype='in', desc='Control variable; 0=subsonic solution, 1=supersonic solution') #ifab = Enum(1, [0, 1], iotype='in', desc='Control variable; 0=back pressure constrained solution, 1=Fabri choke solution') ispm = Enum(0, [0, 1], iotype='in', desc='Control variable; 0=direct solution, 1=iterative closure inlet static pressure matching') iprnt = Int(2, iotype='in', desc='Number of streamwise (x) station printer control, 2=print every station, etc.') ipw = Int(1, iotype='in', desc='Number of cross-stream (y) station printer control, 1=print every variable, etc.') nmax = Int(6, iotype='in', desc='Maximum number of summations used in analytical (Greens function) expansion for marching analytical/numerical decomposition') # Variables for flocond.in # ------------------------- #p01d = Float(8467.2, iotype='in', units='lbf/ft**2', desc='Primary stream total pressure') #p02d = Float(2116.8, iotype='in', units='lbf/ft**2', desc='Secondary stream total pressure') #t01d = Float(1037.38, iotype='in', units='degR', desc='Primary stream total temperature') #t02d = Float(518.69, iotype='in', units='degR', desc='Secondary stream total temperature') #rm1 = Float(1.50, iotype='in', desc='Primary stream Mach number') #rm2 = Float(0.4, iotype='in', desc='Secondary stream Mach number') a1d = Float(6.00, units='ft**2', desc='Primary inlet stream cross-sectional area') a2d = Float(8.40, units='ft**2', desc='Secondary inlet stream cross-sectional area') a3d = Float(13.68, units='ft**2', desc='Exit plane cross-sectional area') rg = Float(1718., iotype='in', units='ft*lb/slug/degR', desc='Real gas constant (air) ((ft lb)/(slug deg R))') #gam = Float(1.4, iotype='in', desc='Specific heat ratio') #pinf = Float(2116.8, iotype='in', units='lbf/ft**2', desc='Ambient static pressure') rec1 = Float(1.0, iotype='in', desc='Primary stream nozzle pressure recovery') rec2 = Float(0.98, iotype='in', desc='Secondary stream nozzle pressure recovery') # Variables for expnd.in # ------------------------- rm1s = Float(1.8, iotype='in', desc='Expanded primary stream Mach number') rm2s = Float(0.8, iotype='in', desc='Expanded secondary stream Mach number') dxe = Float(0.1, iotype='in', desc='Jacobian permutation for Broyden solver, approximately 0.1') relx = Float(1., iotype='in', desc='Relaxation constant (normally not used, set equal to 1.0)') errm = Float(1.E-6, iotype='in', desc='Maximum error in expand routines') nmx = Int(500, iotype='in', desc='Maximum number of iterations in Broyden solver') intt = Int(100, iotype='in', desc='Number of intervals chosen to search for static pressure constrained expansion problem') # Variables for zrdmix.in # ------------------------- BWID = Float(6.0, units='ft', desc='Width of 2-d ejector mixing section') #RLD = Float(10.0, iotype='in', units='ft', desc='Length of mixing section') RLPRNT = Float(0.3333, iotype='in', units='ft', desc='Streamwise (x) location for cross-stream profile print out to file yprmw.out') PR = Float(1.E0, iotype='in', desc='Turbulent Prandtl Number') CGR = Float(1., iotype='in', desc='Streamwise (x) variable grid control parameter: CGR > 1 cluster points in near field, CGR < 1 cluster points in far field, and CGR= 1 constant grid spacing') REVRT = Float(2.0E0, iotype='in', desc='Circulation Reynolds Number') H0LM = Float(2.88, iotype='in', desc='Lobe height to wavelength ratio') H0HY = Float(0.90, iotype='in', desc='Lobe height to mixing section height (from centerline) ratio (chute penetration)') #ALP1 = Float(-10.0, iotype='in', desc='Primary flow angle off of mixing chutes') #ALP2 = Float(-10.0, iotype='in', desc='Secondary flow angle off of mixing chutes') IMAX = Int(5, iotype='in', desc='Number of streamwise (x) grid points') JMAX = Int(20, iotype='in', desc='Number of cross-stream (y) grid points, maximum=30') # Variables for hwall.in # ------------------------- geom = Array(array([[0.0,2.4],[10.0,2.28]]), dtype=numpy_float, iotype='in', desc='x,y nozzle geometry coordinates') # Output variables # ------------------------- GrossThrust = Float(iotype='out', units='lbf', desc='Overall gross thrust') ExitMassFlow = Float(iotype='out', units='lbm/s', desc='Exit mass flow') ExitVelocity = Float(iotype='out', units='ft/s', desc='Exit plane ideally mixed velocity') ExitMach = Float(iotype='out', desc='Exit plane ideally mixed Mach number') ExitStaticTemp = Float(iotype='out', units='degR', desc='Exit plane ideally mixed static temperature') ExitTotalTemp = Float(iotype='out', units='degR', desc='Exit plane ideally mixed total temperature') PumpingRatio = Float(iotype='out', desc='Entrainment ratio w2/w1') CFG = Float(iotype='out', desc='Gross thrust coefficient') PrimaryVelocity = Float(iotype='out', units='ft/s', desc='Primary nozzle velocity') SecondaryVelocity = Float(iotype='out', units='ft/s', desc='Secondary nozzle velocity') PrimaryMassFlow = Float(iotype='out', units='slug/s', desc='Primary nozzle mass flow') SecondaryMassFlow = Float(iotype='out', units='slug/s', desc='Secondary nozzle mass flow') SecondaryMach = Float(iotype='out', desc='Secondary nozzle Mach number') DegreeOfMixing = Float(iotype='out', desc='Degree of mixing in pressure constraint') NPR = Float(iotype='out', desc='Nozzle pressure ratio') def __init__(self): super(DREA,self).__init__() self.command = ['drea'] self.ist = None self.ifab = None self.external_files = [ FileMetadata(path='control.in', input=True), FileMetadata(path='flocond.in', input=True), FileMetadata(path='expnd.in', input=True), FileMetadata(path='zrdmix.in', input=True), FileMetadata(path='hwall.in', input=True), FileMetadata(path='ejectd.out'), FileMetadata(path=self.stderr), ] def _runDREA(self, FabriOrSub): self.generate_input(FabriOrSub) #Remove existing primary output file before execution if os.path.exists("ejectd.out"): os.remove("ejectd.out") #Execute the component super(DREA, self).execute() #Parse output file self.parse_output(FabriOrSub) def setup(self): """ Uses some values in our variable tables to fill in some derived paramters needed by DREA. This is application-specific.""" # Copy Flow parameters from flow_in to flow_out self.flow_out = self.flow_in.copy() self.geo_out = self.geo_in.copy() # Perform area calculations based on input AsAp, AeAt and AR # Note that DREA only uses half the area as it assumes a plane of symmetry self.a1d = self.geo_in.Apri/2 self.a2d = self.geo_in.AsAp*self.geo_in.Apri/2 self.a3d = self.geo_in.AeAt*(self.geo_in.Apri+self.geo_in.Asec)/2 self.BWID = (self.geo_in.AR*(self.geo_in.Apri+self.geo_in.Asec))**0.5 def execute(self): """ Executes our file-wrapped component. """ self.setup() #Prepare the input files for DREA if self.mode != 'Auto': self._runDREA(self.mode) else: #Try Fabri choke solution try: self._runDREA('Fabri') except RuntimeError, err: if "EJECTOR SOLUTION" in str(err): self._runDREA('Subsonic') else: raise(err)
class DistributeSpiral(TopfarmComponent): borders = Array(iotype='in', desc='The polygon defining the borders ndarray([n_bor,2])', unit='m') spiral_param = Float(5.0, iotype='in', desc='spiral parameter') wt_positions = Array( [], unit='m', iotype='out', desc='Array of wind turbines attached to particular positions') inc = 0 def __init__(self, wt_layout, **kwargs): """ baseline = Array(unit='m', iotype='in', desc='Array of wind turbines attached to particular positions') pos = Array(iotype='in', desc='[n_wt]') :param wt_layout: :param borders: :param spiral_param: :return: """ super(DistributeSpiral, self).__init__(**kwargs) self.original_wt_layout = wt_layout self.wt_names = wt_layout.wt_names self.baseline = wt_layout.wt_positions for wt_name in self.wt_names: self.add(wt_name, Float(0.0, iotype='in')) def list_design_variables(self): return [{ 'name': wt_name, 'start': 0.0, 'low': 0.0, 'high': 1.0, 'fd_step': 0.005 } for wt_name in self.wt_names] def execute(self): #if self.inc == 0: # self.polyfill = PolyFill(self.borders, 100, 100) # self.old_positions = self.baseline #self.wt_layout = self.baseline #self.wt_layout.wt_positions += self.pos * scaling #new_positions = self.baseline + self.pos * scaling_dist new_positions = self.baseline.copy() for i, wt_name in enumerate(self.wt_names): opos = getattr(self.original_wt_layout, wt_name).position parameter = getattr(self, wt_name) new_positions[i, :] = opos + spiral(parameter * 10 * np.pi, self.spiral_param, 1.) inc = 0.0 while not point_in_poly(new_positions[i, 0], new_positions[i, 1], self.borders): inc += 0.01 new_positions[i, :] = opos + spiral( (parameter + inc) * 10 * np.pi, self.spiral_param, 1.) self.wt_positions = new_positions #self.wt_positions = self.polyfill.update(self.old_positions, new_positions) self.old_positions = self.wt_positions.copy() self.inc += 1
class CrossSection(XMLContainer): """ XML parameters specific to a cabin cross-section. """ XMLTAG = 'Cabin_Cross_Sections' xs1_p1x = Float(iotype='in', xmltag='Cabin_Point_XS1_P1X', desc='') xs1_p1y = Float(iotype='in', xmltag='Cabin_Point_XS1_P1Y', desc='') xs1_p1z = Float(iotype='in', xmltag='Cabin_Point_XS1_P1Z', desc='') xs1_p2x = Float(iotype='in', xmltag='Cabin_Point_XS1_P2X', desc='') xs1_p2y = Float(iotype='in', xmltag='Cabin_Point_XS1_P2Y', desc='') xs1_p2z = Float(iotype='in', xmltag='Cabin_Point_XS1_P2Z', desc='') xs1_p3x = Float(iotype='in', xmltag='Cabin_Point_XS1_P3X', desc='') xs1_p3y = Float(iotype='in', xmltag='Cabin_Point_XS1_P3Y', desc='') xs1_p3z = Float(iotype='in', xmltag='Cabin_Point_XS1_P3Z', desc='') xs1_p4x = Float(iotype='in', xmltag='Cabin_Point_XS1_P4X', desc='') xs1_p4y = Float(iotype='in', xmltag='Cabin_Point_XS1_P4Y', desc='') xs1_p4z = Float(iotype='in', xmltag='Cabin_Point_XS1_P4Z', desc='') xs2_p1x = Float(iotype='in', xmltag='Cabin_Point_XS2_P1X', desc='') xs2_p1y = Float(iotype='in', xmltag='Cabin_Point_XS2_P1Y', desc='') xs2_p1z = Float(iotype='in', xmltag='Cabin_Point_XS2_P1Z', desc='') xs2_p2x = Float(iotype='in', xmltag='Cabin_Point_XS2_P2X', desc='') xs2_p2y = Float(iotype='in', xmltag='Cabin_Point_XS2_P2Y', desc='') xs2_p2z = Float(iotype='in', xmltag='Cabin_Point_XS2_P2Z', desc='') xs2_p3x = Float(iotype='in', xmltag='Cabin_Point_XS2_P3X', desc='') xs2_p3y = Float(iotype='in', xmltag='Cabin_Point_XS2_P3Y', desc='') xs2_p3z = Float(iotype='in', xmltag='Cabin_Point_XS2_P3Z', desc='') xs2_p4x = Float(iotype='in', xmltag='Cabin_Point_XS2_P4X', desc='') xs2_p4y = Float(iotype='in', xmltag='Cabin_Point_XS2_P4Y', desc='') xs2_p4z = Float(iotype='in', xmltag='Cabin_Point_XS2_P4Z', desc='') def __init__(self): super(CrossSection, self).__init__(self.XMLTAG)
class PrintOutputs(TopfarmComponent): wt_positions = Array( [], unit='m', iotype='in', desc='Array of wind turbines attached to particular positions') baseline = Array( [], unit='m', iotype='in', desc='Array of wind turbines attached to particular positions') borders = Array(iotype='in', desc='The polygon defining the borders ndarray([n_bor,2])', unit='m') depth = Array(iotype='in', desc='An array of depth ndarray([n_d, 2])', unit='m') foundation_length = Float( iotype='in', desc='The total foundation length of the wind farm') foundations = Array(iotype='in', desc='The foundation length ofeach wind turbine') wt_dist = Array( iotype='in', desc="""The distance between each turbines ndarray([n_wt, n_wt]).""", unit='m') spiral_param = Float(5.0, iotype='in', desc='spiral parameter') png_name = Str('wind_farm', iotype='in', desc='The base of the png name used to save the fig') result_file = Str('wind_farm', iotype='in', desc='The base result name used to save the fig') net_aep = Float(iotype='in', desc='') distribution = Str('spiral', iotype='in', desc='The type of distribution to plot') elnet_layout = Dict(iotype='in') elnet_length = Float(iotype='in') inc = 0 fs = 15 #Font size def execute(self): dist_min = np.array( [self.wt_dist[i] for i in range(self.wt_dist.shape[0])]).min() dist_mean = np.array( [self.wt_dist[i] for i in range(self.wt_dist.shape[0])]).mean() if self.inc == 0: try: pa(self.result_file + '.results').remove() except: pass self.iterations = [self.inc] self.targvalue = [[ self.foundation_length, self.elnet_length, dist_mean, dist_min, self.net_aep ]] else: self.iterations.append(self.inc) self.targvalue.append([ self.foundation_length, self.elnet_length, dist_mean, dist_min, self.net_aep ]) self.targname = [ 'Foundation length', 'El net length', 'Mean WT Dist', 'Min WT Dist', 'AEP' ] targarr = np.array(self.targvalue) output = '%d:' % (self.inc) + ', '.join([ '%s=%6.2f' % (self.targname[i], targarr[-1, i]) for i in range(len(self.targname)) ]) + '\n' # + str(self.wt_positions) print output with open(self.result_file + '.results', 'a') as f: f.write(output) self.inc += 1
class RegionVT(VariableTree): c0 = Float() c1 = Float()
class SellarBLISS(Assembly): """ Optimization of the Sellar problem using the BLISS algorithm Disciplines coupled with FixedPointIterator. """ z_store = Array([0, 0], dtype=Float) x1_store = Float(0.0) def configure(self): """ Creates a new Assembly with this problem Optimal Design at (1.9776, 0, 0) Optimal Objective = 3.18339""" # Disciplines self.add('dis1', sellar.Discipline1()) self.add('dis2', sellar.Discipline2()) objective = '(dis1.x1)**2 + dis1.z2 + dis1.y1 + exp(-dis2.y2)' constraint1 = 'dis1.y1 > 3.16' constraint2 = 'dis2.y2 < 24.0' # Top level is Fixed-Point Iteration self.add('driver', FixedPointIterator()) self.driver.add_parameter('dis1.x1', low=0.0, high=10.0, start=1.0) self.driver.add_parameter(['dis1.z1', 'dis2.z1'], low=-10.0, high=10.0, start=5.0) self.driver.add_parameter(['dis1.z2', 'dis2.z2'], low=0.0, high=10.0, start=2.0) self.driver.add_constraint('x1_store = dis1.x1') self.driver.add_constraint('z_store[0] = dis1.z1') self.driver.add_constraint('z_store[1] = dis1.z2') self.driver.max_iteration = 50 self.driver.tolerance = .001 # Multidisciplinary Analysis self.add('mda', BroydenSolver()) self.mda.add_parameter('dis1.y2', low=-9.e99, high=9.e99, start=0.0) self.mda.add_constraint('dis2.y2 = dis1.y2') self.mda.add_parameter('dis2.y1', low=-9.e99, high=9.e99, start=3.16) self.mda.add_constraint('dis2.y1 = dis1.y1') # Discipline 1 Sensitivity Analysis self.add('sa_dis1', SensitivityDriver()) self.sa_dis1.workflow.add(['dis1']) self.sa_dis1.add_parameter('dis1.x1', low=0.0, high=10.0, fd_step=.001) self.sa_dis1.add_constraint(constraint1) self.sa_dis1.add_constraint(constraint2) self.sa_dis1.add_objective(objective, name='obj') self.sa_dis1.differentiator = FiniteDifference() self.sa_dis1.default_stepsize = 1.0e-6 # Discipline 2 Sensitivity Analysis # dis2 has no local parameter, so there is no need to treat it as # a subsystem. # System Level Sensitivity Analysis # Note, we cheat here and run an MDA instead of solving the # GSE equations. Have to put this on the TODO list. self.add('ssa', SensitivityDriver()) self.ssa.workflow.add(['mda']) self.ssa.add_parameter(['dis1.z1', 'dis2.z1'], low=-10.0, high=10.0) self.ssa.add_parameter(['dis1.z2', 'dis2.z2'], low=0.0, high=10.0) self.ssa.add_constraint(constraint1) self.ssa.add_constraint(constraint2) self.ssa.add_objective(objective, name='obj') self.ssa.differentiator = FiniteDifference() self.ssa.default_stepsize = 1.0e-6 # Discipline Optimization # (Only discipline1 has an optimization input) self.add('bbopt1', CONMINdriver()) self.bbopt1.add_parameter('x1_store', low=0.0, high=10.0, start=1.0) self.bbopt1.add_objective( 'sa_dis1.F[0] + sa_dis1.dF[0][0]*(x1_store-dis1.x1)') self.bbopt1.add_constraint( 'sa_dis1.G[0] + sa_dis1.dG[0][0]*(x1_store-dis1.x1) < 0') #this one is technically unncessary self.bbopt1.add_constraint( 'sa_dis1.G[1] + sa_dis1.dG[1][0]*(x1_store-dis1.x1) < 0') self.bbopt1.add_constraint('(x1_store-dis1.x1)<.5') self.bbopt1.add_constraint('(x1_store-dis1.x1)>-.5') self.bbopt1.iprint = 0 self.bbopt1.linobj = True # Global Optimization self.add('sysopt', CONMINdriver()) self.sysopt.add_parameter('z_store[0]', low=-10.0, high=10.0, start=5.0) self.sysopt.add_parameter('z_store[1]', low=0.0, high=10.0, start=2.0) self.sysopt.add_objective( 'ssa.F[0]+ ssa.dF[0][0]*(z_store[0]-dis1.z1) + ssa.dF[0][1]*(z_store[1]-dis1.z2)' ) self.sysopt.add_constraint( 'ssa.G[0] + ssa.dG[0][0]*(z_store[0]-dis1.z1) + ssa.dG[0][1]*(z_store[1]-dis1.z2) < 0' ) self.sysopt.add_constraint( 'ssa.G[1] + ssa.dG[1][0]*(z_store[0]-dis1.z1) + ssa.dG[1][1]*(z_store[1]-dis1.z2) < 0' ) self.sysopt.add_constraint('z_store[0]-dis1.z1<.5') self.sysopt.add_constraint('z_store[0]-dis1.z1>-.5') self.sysopt.add_constraint('z_store[1]-dis1.z2<.5') self.sysopt.add_constraint('z_store[1]-dis1.z2>-.5') self.sysopt.iprint = 0 self.sysopt.linobj = True self.driver.workflow = SequentialWorkflow() self.driver.workflow.add(['ssa', 'sa_dis1', 'bbopt1', 'sysopt'])
def __init__(self, **metadata): self._vals = {} Float.__init__(self, **metadata) self._metadata['type'] = 'property' # Just to show correct type.