def set(self, name, value): if name in self.descriptions: if self.types[name] == "string_list": self.values[name] = stringToStringList(value) elif self.types[name] == "bool": self.values[name] = stringToBool(value) elif self.types[name] == "int": self.values[name] = stringToInt(value) elif self.types[name] == "float": self.values[name] = stringToFloat(value) elif self.types[name] == "function": self.values[name] = value elif self.types[name] == "general": self.values[name] = value elif self.types[name] == "parsed_function": self.values[name] = stringToFunction(value) elif self.types[name] == "string": self.values[name] = value elif self.types[name] == "StringSelection": if value in self.string_selections[name]: self.values[name] = value else: selection_list_string = "" for acceptable_value in self.string_selections[name]: selection_list_string += "\n " + acceptable_value error("The parameter '" + name + "' must take one of the following values:" + selection_list_string) else: error("The parameter '" + name + "' is not registered.")
def __init__(self, params): Executioner.__init__(self, params) # determine how time step size is determined if params.has("dt") and params.has("cfl"): error("The parameters 'dt' and 'cfl' cannot both be provided.") elif params.has("dt"): self.dt_nominal = params.get("dt") self.use_cfl_dt = False elif params.has("cfl"): self.cfl = params.get("cfl") self.use_cfl_dt = True self.cfl_dt_aux_list = self.createCFLAuxQuantities() self.cfl_aux_names = [aux.name for aux in self.cfl_dt_aux_list] else: error("Either parameter 'dt' or 'cfl' must be provided.") self.end_time = params.get("end_time") self.lump_mass_matrix = params.get("lump_mass_matrix") self.verbose = params.get("verbose") # tolerance to prevent small final time steps due to floating point precision error self.end_tolerance = 1e-12 self.U_old = deepcopy(self.U) self.M = self.computeMassMatrix()
def stringToStringList(s): if isinstance(s, basestring): return s.split() elif isinstance(s, list): return s else: error("'" + s + "' is not a valid string list.")
def __init__(self, params): FreeBCJunction.__init__(self, params) if self.n_meshes != 2: error("Only implemented for connecting 2 meshes.") self.n_var = self.dof_handler.n_var self.n_constraints += self.n_var
def __init__(self, params): Junction.__init__(self, params) if self.n_meshes != 2: error("CloneJunction is only implemented for connecting 2 meshes.") # assume that first mesh is the "master" self.k_master = self.node_indices[0] self.k_slave = self.node_indices[1]
def stringToBool(s): if s == "True" or s == True: return True elif s == "False" or s == False: return False else: error("'" + s + "' is not a valid boolean.") return value
def get(self, name): if name in self.values: return self.values[name] else: if name in self.descriptions: error("The parameter '" + name + "' was not set and does not have a default.") else: error("'" + name + "' is not a registered parameter.")
def createObjectFromParametersObject(self, object_class, parameters_object): # create the object if object_class in globals(): constructor = globals()[object_class] else: error("'" + object_class + "' is not a valid object type.") the_object = constructor(parameters_object) return the_object
def __init__(self, params): AuxQuantity.__init__(self, params) self.name = params.get("var") self.other_vars = params.get("other_vars") self.coefs = params.get("coefs") self.b = params.get("b") if len(self.other_vars) != len(self.coefs): error( "'other_vars' and 'coefs' list parameters must have same length." ) self.n = len(self.other_vars)
def registerParameterInternal(self, name, param_type, description, default): self.types[name] = param_type if name == "type": error( "'type' is a reserved name and cannot be used for a parameter name." ) if name in self.descriptions: error("The parameter '" + name + "' has already been registered.") else: self.descriptions[name] = description if default != None: self.values[name] = default
def __str__(self): # make sure that all properties have been computed if not self.computed_all_properties: error("The thermodynamic properties still need to be computed.") # create and return string printout = "\nFluid properties (SI Units):\n" printout += " p = " + str(self.values["p"]) + "\n" printout += " T = " + str(self.values["T"]) + "\n" printout += " rho = " + str(self.values["rho"]) + "\n" printout += " v = " + str(self.values["v"]) + "\n" printout += " e = " + str(self.values["e"]) + "\n" return printout
def __init__(self, params): Junction1Phase.__init__(self, params) if self.n_meshes != 2: error("CompressibleJunction is only implemented for connecting 2 meshes.") # determine if momentum flux balance is to be used for last equation; # otherwise, stagnation pressure condition will be used self.use_momentum_flux_balance = params.get("use_momentum_flux_balance") # get node indices self.k_left = self.node_indices[0] self.k_right = self.node_indices[1] self.k_left_adjacent = self.adjacent_node_indices[0] self.k_right_adjacent = self.adjacent_node_indices[1]
def computeRemainingProperties(self, eos): if self.provided["p"] and self.provided["T"]: self.values["rho"] = eos.rho(self.values["p"], self.values["T"]) self.values["v"] = 1.0 / self.values["rho"] self.values["e"] = eos.e(self.values["v"], self.values["p"])[0] elif self.provided["p"] and self.provided["rho"]: self.values["v"] = 1.0 / self.values["rho"] self.values["e"] = eos.e(self.values["v"], self.values["p"])[0] self.values["T"] = eos.T(self.values["v"], self.values["e"])[0] else: error( "The provided combination of thermodynamic properties has not been implemented." ) self.computed_all_properties = True
def __init__(self, params): self.A = params.get("A") self.p = [params.get("p")] self.u = [params.get("u")] # one may supply either rho or T, but not both if params.has("rho") and params.has("T"): error("ICs cannot specify both T and rho.") elif params.has("rho"): self.rho = [params.get("rho")] self.specified_rho = True elif params.has("T"): self.T = [params.get("T")] self.specified_rho = False else: error("Either 'rho' or 'T' must be specified for IC.")
def __init__(self, params): self.provided = dict() self.values = dict() self.getPropertyIfAvailable("rho", params) self.getPropertyIfAvailable("T", params) self.getPropertyIfAvailable("p", params) # count the number of provided properties n_provided_properties = 0 for prop in self.provided: if self.provided[prop]: n_provided_properties += 1 if n_provided_properties != 2: error("Exactly 2 thermodynamic properties must be provided.") # flag that all thermodynamic properties have been computed self.computed_all_properties = False
def createParametersObject(self, object_class, params=None): # parameters classes are always named as the object class plus "Parameters" parameters_class = object_class + "Parameters" # parameters classes should have no arguments to their constructors if parameters_class in globals(): constructor = globals()[parameters_class] else: error("'" + parameters_class + "' is not a valid object type.") parameters_object = constructor() # set each of the parameters if params: for param in params: if param != "type": parameters_object.set(param, params[param]) return parameters_object
def __init__(self, params): self.mesh_names = params.get("mesh_names") self.mesh_sides = params.get("mesh_sides") self.dof_handler = params.get("dof_handler") self.eos_list = params.get("eos_list") self.model_type = self.dof_handler.model_type # ensure that lengths of list parameters agree self.n_meshes = len(self.mesh_names) if len(self.mesh_names) != len(self.mesh_sides): error( "The list parameters 'mesh_names' and 'mesh_sides' must have the same size." ) # get node indices and adjacent node indices self.node_indices = list() self.adjacent_node_indices = list() for i, mesh_name in enumerate(self.mesh_names): if self.mesh_sides[i] == "left": self.node_indices.append( self.dof_handler.getNodeIndexFromLeft(mesh_name, 0)) self.adjacent_node_indices.append( self.dof_handler.getNodeIndexFromLeft(mesh_name, 1)) elif self.mesh_sides[i] == "right": self.node_indices.append( self.dof_handler.getNodeIndexFromRight(mesh_name, 0)) self.adjacent_node_indices.append( self.dof_handler.getNodeIndexFromRight(mesh_name, 1)) else: error("Side parameters must be either 'left' or 'right'.") # get normal vectors self.nx = list() for i in xrange(self.n_meshes): if self.mesh_sides[i] == "left": self.nx.append(-1.0) else: self.nx.append(1.0) # initialize number of constraints to zero self.n_constraints = 0
def __init__(self, params): self.A = params.get("A") self.vf1 = params.get("vf1") self.p = [params.get("p1"), params.get("p2")] self.u = [params.get("u1"), params.get("u2")] # one may supply either rho or T, but not both if params.has("rho1") and params.has("rho2"): has_rho = True else: has_rho = False if params.has("T1") and params.has("T2"): has_T = True else: has_T = False if (params.has("T1") and params.has("rho2")) or (params.has("rho1") and params.has("T2")): error("ICs cannot supply a mix of T and rho between the phases.") elif has_rho and has_T: error("ICs cannot specify both T and rho.") elif has_rho: self.rho = [params.get("rho1"), params.get("rho2")] self.specified_rho = True elif has_T: self.T = [params.get("T1"), params.get("T2")] self.specified_rho = False else: error( "Either 'rho' or 'T' for each phase must be specified for IC.")
def assertNonNegativeSoundSpeedArgSingle(arg, p, v): if arg < 0: error("Sound speed: negative x in sqrt(x), where x = gamma * (p + p_inf) * v:\n" + "p = " + str(p) + "\nv = " + str(v))
def applyStronglyToNonlinearSystem(self, U_new, U_old, r, J): n_values = 6 L = 0 R = 1 L_old = 2 R_old = 3 LL_old = 4 RR_old = 5 k = [0] * n_values k[L] = self.k_left k[R] = self.k_right k[L_old] = self.k_left k[R_old] = self.k_right k[LL_old] = self.k_left_adjacent k[RR_old] = self.k_right_adjacent i_arhoA = [0] * n_values i_arhoA[L] = self.i_arhoL i_arhoA[R] = self.i_arhoR i_arhoA[L_old] = self.i_arhoL i_arhoA[R_old] = self.i_arhoR i_arhoA[LL_old] = self.i_arhoLL i_arhoA[RR_old] = self.i_arhoRR i_arhouA = [0] * n_values i_arhouA[L] = self.i_arhouAL i_arhouA[R] = self.i_arhouAR i_arhouA[L_old] = self.i_arhouAL i_arhouA[R_old] = self.i_arhouAR i_arhouA[LL_old] = self.i_arhouALL i_arhouA[RR_old] = self.i_arhouARR i_arhoEA = [0] * n_values i_arhoEA[L] = self.i_arhoEAL i_arhoEA[R] = self.i_arhoEAR i_arhoEA[L_old] = self.i_arhoEAL i_arhoEA[R_old] = self.i_arhoEAR i_arhoEA[LL_old] = self.i_arhoEALL i_arhoEA[RR_old] = self.i_arhoEARR U = [0] * n_values U[L] = U_new U[R] = U_new U[L_old] = U_old U[R_old] = U_old U[LL_old] = U_old U[RR_old] = U_old # initialize lists rho = [0] * n_values drho_daA1 = [0] * n_values drho_darhoA = [0] * n_values u = [0] * n_values du_darhoA = [0] * n_values du_darhouA = [0] * n_values e = [0] * n_values de_darhoA = [0] * n_values de_darhouA = [0] * n_values de_darhoEA = [0] * n_values p = [0] * n_values dp_daA1 = [0] * n_values dp_darhoA = [0] * n_values dp_darhouA = [0] * n_values dp_darhoEA = [0] * n_values c = [0] * n_values dc_daA1 = [0] * n_values dc_darhoA = [0] * n_values dc_darhouA = [0] * n_values dc_darhoEA = [0] * n_values if not self.use_momentum_flux_balance: p0 = [0] * n_values dp0_daA1 = [0] * n_values dp0_darhoA = [0] * n_values dp0_darhouA = [0] * n_values dp0_darhoEA = [0] * n_values # loop over subscript/superscript combinations for i in xrange(n_values): A = self.dof_handler.A[k[i]] aA1 = self.dof_handler.aA1(U[i], k[i]) vf, dvf_daA1 = computeVolumeFraction(aA1, A, self.phase, self.model_type) arhoA = U[i][i_arhoA[i]] arhouA = U[i][i_arhouA[i]] arhoEA = U[i][i_arhoEA[i]] rho[i], drho_dvf, drho_darhoA[i], _ = computeDensity(vf, arhoA, A) drho_daA1[i] = drho_dvf * dvf_daA1 u[i], du_darhoA[i], du_darhouA[i] = computeVelocity(arhoA, arhouA) v, dv_drho = computeSpecificVolume(rho[i]) dv_daA1 = dv_drho * drho_daA1[i] dv_darhoA = dv_drho * drho_darhoA[i] E, dE_darhoA, dE_darhoEA = computeSpecificTotalEnergy(arhoA, arhoEA) e[i], de_du, de_dE = computeSpecificInternalEnergy(u[i], E) de_darhoA[i] = de_du * du_darhoA[i] + de_dE * dE_darhoA de_darhouA[i] = de_du * du_darhouA[i] de_darhoEA[i] = de_dE * dE_darhoEA p[i], dp_dv, dp_de = self.eos.p(v, e[i]) dp_daA1[i] = dp_dv * dv_daA1 dp_darhoA[i] = dp_dv * dv_darhoA + dp_de * de_darhoA[i] dp_darhouA[i] = dp_de * de_darhouA[i] dp_darhoEA[i] = dp_de * de_darhoEA[i] c[i], dc_dv, dc_de = self.eos.c(v, e[i]) dc_daA1[i] = dc_dv * dv_daA1 dc_darhoA[i] = dc_dv * dv_darhoA + dc_de * de_darhoA[i] dc_darhouA[i] = dc_de * de_darhouA[i] dc_darhoEA[i] = dc_de * de_darhoEA[i] if not self.use_momentum_flux_balance: s, ds_dv, ds_de = self.eos.s(v, e[i]) ds_daA1 = ds_dv * dv_daA1 ds_darhoA = ds_dv * dv_darhoA + ds_de * de_darhoA[i] ds_darhouA = ds_de * de_darhouA[i] ds_darhoEA = ds_de * de_darhoEA[i] h, dh_de, dh_dp, dh_drho = computeSpecificEnthalpy(e[i], p[i], rho[i]) dh_daA1 = dh_dp * dp_daA1[i] dh_darhoA = dh_de * de_darhoA[i] + dh_dp * dp_darhoA[i] + dh_drho * drho_darhoA[i] dh_darhouA = dh_de * de_darhouA[i] + dh_dp * dp_darhouA[i] dh_darhoEA = dh_de * de_darhoEA[i] + dh_dp * dp_darhoEA[i] h0 = h + 0.5 * u[i]**2 dh0_daA1 = dh_daA1 dh0_darhoA = dh_darhoA + u[i] * du_darhoA[i] dh0_darhouA = dh_darhouA + u[i] * du_darhouA[i] dh0_darhoEA = dh_darhoEA p0[i], dp0_dh0, dp0_ds = self.eos.p_from_h_s(h0, s) dp0_daA1[i] = dp0_dh0 * dh0_daA1 + dp0_ds * ds_daA1 dp0_darhoA[i] = dp0_dh0 * dh0_darhoA + dp0_ds * ds_darhoA dp0_darhouA[i] = dp0_dh0 * dh0_darhouA + dp0_ds * ds_darhouA dp0_darhoEA[i] = dp0_dh0 * dh0_darhoEA + dp0_ds * ds_darhoEA # compute old average quantities rhoL = 0.5 * (rho[L_old] + rho[LL_old]) rhoR = 0.5 * (rho[R_old] + rho[RR_old]) uL = 0.5 * (u[L_old] + u[LL_old]) uR = 0.5 * (u[R_old] + u[RR_old]) pL = 0.5 * (p[L_old] + p[LL_old]) pR = 0.5 * (p[R_old] + p[RR_old]) cL = 0.5 * (c[L_old] + c[LL_old]) cR = 0.5 * (c[R_old] + c[RR_old]) # residual indices i1 = self.i_arhoL i2 = self.i_arhouAL i3 = self.i_arhoEAL i4 = self.i_arhoR i5 = self.i_arhouAR i6 = self.i_arhoEAR # reset Jacobian rows J[i1,:] = 0 J[i2,:] = 0 J[i3,:] = 0 J[i4,:] = 0 J[i5,:] = 0 J[i6,:] = 0 # compute residuals and Jacobians r[i1] = p[L] - pL + rhoL * (cL - uL) * (u[L] - uL) J_i1_vf1L = dp_daA1[L] J[i1,self.i_arhoL] = dp_darhoA[L] + rhoL * (cL - uL) * du_darhoA[L] J[i1,self.i_arhouAL] = dp_darhouA[L] + rhoL * (cL - uL) * du_darhouA[L] J[i1,self.i_arhoEAL] = dp_darhoEA[L] r[i2] = p[R] - pR - rhoR * (cR - uR) * (u[R] - uR) J_i2_vf1R = dp_daA1[R] J[i2,self.i_arhoR] = dp_darhoA[R] - rhoR * (cR - uR) * du_darhoA[R] J[i2,self.i_arhouAR] = dp_darhouA[R] - rhoR * (cR - uR) * du_darhouA[R] J[i2,self.i_arhoEAR] = dp_darhoEA[R] if u[L] >= 0: if u[R] < 0: error("Assumption violated: Both velocity conditions were true.") r[i3] = rho[L] - rhoL - (p[L] - pL) / cL**2 J_i3_vf1L = drho_daA1[L] - dp_daA1[L] / cL**2 J_i3_vf1R = 0 J[i3,self.i_arhoL] = drho_darhoA[L] - dp_darhoA[L] / cL**2 J[i3,self.i_arhouAL] = - dp_darhouA[L] / cL**2 J[i3,self.i_arhoEAL] = - dp_darhoEA[L] / cL**2 elif u[R] < 0: r[i3] = rho[R] - rhoR - (p[R] - pR) / cR**2 J_i3_vf1R = drho_daA1[R] - dp_daA1[R] / cR**2 J_i3_vf1L = 0 J[i3,self.i_arhoR] = drho_darhoA[R] - dp_darhoA[R] / cR**2 J[i3,self.i_arhouAR] = - dp_darhouA[R] / cR**2 J[i3,self.i_arhoEAR] = - dp_darhoEA[R] / cR**2 else: error("Assumption violated: Neither velocity condition was true.") r[i4] = rho[L] * u[L] - rho[R] * u[R] J_i4_vf1L = drho_daA1[L] * u[L] J[i4,self.i_arhoL] = drho_darhoA[L] * u[L] + rho[L] * du_darhoA[L] J[i4,self.i_arhouAL] = rho[L] * du_darhouA[L] J_i4_vf1R = -drho_daA1[R] * u[R] J[i4,self.i_arhoR] = -(drho_darhoA[R] * u[R] + rho[R] * du_darhoA[R]) J[i4,self.i_arhouAR] = -rho[R] * du_darhouA[R] r[i5] = e[L] + p[L] / rho[L] + 0.5 * u[L]**2 - (e[R] + p[R] / rho[R] + 0.5 * u[R]**2) J_i5_vf1L = dp_daA1[L] / rho[L] - p[L] / rho[L]**2 * drho_daA1[L] J[i5,self.i_arhoL] = de_darhoA[L] + dp_darhoA[L] / rho[L] - p[L] / rho[L]**2 * drho_darhoA[L] + u[L] * du_darhoA[L] J[i5,self.i_arhouAL] = de_darhouA[L] + dp_darhouA[L] / rho[L] + u[L] * du_darhouA[L] J[i5,self.i_arhoEAL] = de_darhoEA[L] + dp_darhoEA[L] / rho[L] J_i5_vf1R = -(dp_daA1[R] / rho[R] - p[R] / rho[R]**2 * drho_daA1[R]) J[i5,self.i_arhoR] = -(de_darhoA[R] + dp_darhoA[R] / rho[R] - p[R] / rho[R]**2 * drho_darhoA[R] + u[R] * du_darhoA[R]) J[i5,self.i_arhouAR] = -(de_darhouA[R] + dp_darhouA[R] / rho[R] + u[R] * du_darhouA[R]) J[i5,self.i_arhoEAR] = -(de_darhoEA[R] + dp_darhoEA[R] / rho[R]) if self.use_momentum_flux_balance: r[i6] = rho[L] * u[L]**2 + p[L] - (rho[R] * u[R]**2 + p[R]) J_i6_vf1L = drho_daA1[L] * u[L]**2 + dp_daA1[L] J[i6,self.i_arhoL] = drho_darhoA[L] * u[L]**2 + rho[L] * 2.0 * u[L] * du_darhoA[L] + dp_darhoA[L] J[i6,self.i_arhouAL] = rho[L] * 2.0 * u[L] * du_darhouA[L] + dp_darhouA[L] J[i6,self.i_arhoEAL] = dp_darhoEA[L] J_i6_vf1R = -(drho_daA1[R] * u[R]**2 + dp_daA1[R]) J[i6,self.i_arhoR] = -(drho_darhoA[R] * u[R]**2 + rho[R] * 2.0 * u[R] * du_darhoA[R] + dp_darhoA[R]) J[i6,self.i_arhouAR] = -(rho[R] * 2.0 * u[R] * du_darhouA[R] + dp_darhouA[R]) J[i6,self.i_arhoEAR] = -dp_darhoEA[R] else: r[i6] = p0[L] - p0[R] J_i6_vf1L = dp0_daA1[L] J[i6,self.i_arhoL] = dp0_darhoA[L] J[i6,self.i_arhouAL] = dp0_darhouA[L] J[i6,self.i_arhoEAL] = dp0_darhoEA[L] J_i6_vf1R = -dp0_daA1[R] J[i6,self.i_arhoR] = -dp0_darhoA[R] J[i6,self.i_arhouAR] = -dp0_darhouA[R] J[i6,self.i_arhoEAR] = -dp0_darhoEA[R] if self.model_type == ModelType.TwoPhase: J[i1,self.i_aA1L] = J_i1_vf1L J[i2,self.i_aA1R] = J_i2_vf1R J[i3,self.i_aA1L] = J_i3_vf1L J[i3,self.i_aA1R] = J_i3_vf1R J[i4,self.i_aA1L] = J_i4_vf1L J[i4,self.i_aA1R] = J_i4_vf1R J[i5,self.i_aA1L] = J_i5_vf1L J[i5,self.i_aA1R] = J_i5_vf1R J[i6,self.i_aA1L] = J_i6_vf1L J[i6,self.i_aA1R] = J_i6_vf1R
def performFinalChecks(self): if self.level != 0: error("All blocks and sub-blocks must be ended with '[]'.")
def applyStronglyToLinearSystemMatrix(self, A): error("Not implemented")
def assertBlockExists(self, block): if not block in self.block_data: error("The block '" + block + "' does not exist.")
def stringToInt(s): try: value = int(s) except: error("'" + s + "' is not a valid integer.") return value
def assertSubblockExists(self, block, subblock): self.assertBlockExists(block) if not subblock in self.subblock_data[block]: error("The subblock '" + subblock + "' does not exist in block '" + block + "'.")
def checkJacobian(self, test_option, model_type=ModelType.OnePhase, phase=0, junction_params=dict(), fd_eps=1e-8): # factory factory = Factory() # meshes params1 = {"n_cell": 1, "name": "mesh1"} params2 = {"n_cell": 1, "name": "mesh2"} meshes = [ factory.createObject("UniformMesh", params1), factory.createObject("UniformMesh", params2) ] # area function def A(x): return 0.2 # DoF handler dof_handler_params = {"meshes": meshes, "A": A} if model_type == ModelType.OnePhase: dof_handler_class = "DoFHandler1Phase" elif model_type == ModelType.TwoPhaseNonInteracting: dof_handler_class = "DoFHandler2PhaseNonInteracting" def vf1_initial(x): return 0.3 dof_handler_params["initial_vf1"] = vf1_initial elif model_type == ModelType.TwoPhase: dof_handler_class = "DoFHandler2Phase" dof_handler = factory.createObject(dof_handler_class, dof_handler_params) n_dof = dof_handler.n_dof # equation of state eos_params1 = {"slope_initial": 1.0, "slope_increment": 0.1} eos_list = [factory.createObject("TestEoS", eos_params1)] if model_type != ModelType.OnePhase: eos_params2 = {"slope_initial": 1.1, "slope_increment": 0.07} eos_list.append(factory.createObject("TestEoS", eos_params2)) # junction junction_params["mesh_names"] = " ".join( [mesh.name for mesh in meshes]) junction_params["mesh_sides"] = "right left" junction_params["dof_handler"] = dof_handler junction_params["eos_list"] = eos_list junction_parameters = factory.createParametersObject( self.junction_name) for param in junction_params: junction_parameters.set(param, junction_params[param]) if junction_parameters.hasRegisteredParam("phase"): junction_parameters.set("phase", phase) junction = factory.createObjectFromParametersObject( self.junction_name, junction_parameters) # update DoF handler with junction constraints dof_handler.updateWithJunctionConstraints([junction]) # compute base solution U = np.zeros(n_dof) U_old = np.zeros(n_dof) for i in xrange(n_dof): U[i] = i + 1.0 U_old[i] = i + 2.0 # determine evaluation function if test_option == "weak": f = junction.applyWeaklyToNonlinearSystem elif test_option == "strong": f = junction.applyStronglyToNonlinearSystem elif test_option == "both": def f(*args, **kwargs): junction.applyWeaklyToNonlinearSystem(*args, **kwargs) junction.applyStronglyToNonlinearSystem(*args, **kwargs) else: error("Invalid test option") # base calculation r = np.zeros(n_dof) J_hand_coded = np.zeros(shape=(n_dof, n_dof)) f(U, U_old, r, J_hand_coded) # finite difference Jacobians rel_diffs = np.zeros(shape=(n_dof, n_dof)) J_fd = np.zeros(shape=(n_dof, n_dof)) for j in xrange(n_dof): # perturb solution U_perturbed = deepcopy(U) U_perturbed[j] += fd_eps # compute finite difference Jacobian r_perturbed = np.zeros(n_dof) J_perturbed = np.zeros(shape=(n_dof, n_dof)) f(U_perturbed, U_old, r_perturbed, J_perturbed) for i in xrange(n_dof): J_fd[i, j] = (r_perturbed[i] - r[i]) / fd_eps # compute difference matrices abs_diffs = abs(J_hand_coded - J_fd) rel_diffs = computeRelativeDifferenceMatrix(J_hand_coded, J_fd) # print results if self.verbose: print "\nRelative difference of Jacobian for " + test_option + " contributions:" printRelativeMatrixDifference(rel_diffs, abs_diffs, 1e-1, 1e-3) matched = np.zeros((n_dof, n_dof), dtype=bool) for i in xrange(n_dof): for j in xrange(n_dof): matched[i, j] = abs_diffs[i, j] < self.abs_tol or rel_diffs[ i, j] < self.rel_tol return matched
def stringToFloat(s): try: value = float(s) except: error("'" + s + "' is not a valid float.") return value
def __init__(self, params): Junction1Phase.__init__(self, params) if self.n_meshes != 2: error("FluxJunction is only implemented for connecting 2 meshes.")
def checkFileExists(filename): if not os.path.isfile(filename): error("The file '" + filename + "' does not exist.")
def applyStronglyToLinearSystemRHSVector(self, U_old, b): error("Not implemented")