def ex6(N, hk): r""" Compute the integral of :math:`x*y*y` over the reference triangle Parameters ---------- N : int Order of base quadrature rule hk : double submesh element diameter """ quad = Quadrature.GaussTriangle(N) comp_quad = Quadrature.CompositeTriangle(quad, hk) N = int(np.ceil(old_div(1, hk))) quad_points = np.asarray(quad.points, 'd') quad_weights = np.asarray(quad.weights, 'd') ii_quad = np.sum(quad_weights * quad_points[:, 0] * quad_points[:, 1] * quad_points[:, 1]) ii_comp_quad = np.sum(comp_quad.weights * comp_quad.points[:, 0] * comp_quad.points[:, 1] * comp_quad.points[:, 1]) ee = np.abs(ii_quad - ii_comp_quad) logEvent("hk=%f\t quad-int=%f\t comp-quad-int=%f error=%f" % (old_div(1.0, N), ii_quad, ii_comp_quad, ee)) return old_div(1.0, N), ee
def unitSimplex(nd=2): """Builds a 2 or 3 dimension reference element. Parameters ---------- nd : int The elements dimension (must be 2 or 3) Returns ------- reference_element """ if nd != 2 and nd != 3: logEvent("ERROR - Reference element must have dimension 2 or 3") sys.exit(1) if nd == 2: return PlanarStraightLineGraphDomain(vertices=[[0., 0.], [0., 1.], [1., 0.]], segments=[[0, 1], [1, 2], [2, 0]], name="Reference Triangle") if nd == 3: boundaryTags = {'bottom': 1, 'front': 2, 'side': 3, 'back': 4} return PiecewiseLinearComplexDomain( vertices=[[0.0, 0.0, 0.0], [1.0, 0.0, 0.0], [0.0, 1.0, 0.0], [0.0, 0.0, 1.0]], facets=[[[0, 2, 3]], [[0, 1, 2]], [[0, 1, 3]], [[1, 2, 3]]], # facetFlags=[boundaryTags['bottom'], # boundaryTags['front'], # boundaryTags['side'], # boundaryTags['back']], name="Reference Simplex")
def ex4(N, hk): r""" Compute the integral of :math:`x` over the reference triangle Parameters ---------- N : int Order of base quadrature rule hk : double submesh element diameter """ quad = Quadrature.GaussTriangle(N) comp_quad = Quadrature.CompositeTriangle(quad, hk) N = int(np.ceil(1 / hk)) quad_points = np.asarray(quad.points, 'd') quad_weights = np.asarray(quad.weights, 'd') ii_quad = np.sum(quad_weights * quad_points[:, 0]) ii_comp_quad = np.sum(comp_quad.weights * comp_quad.points[:, 0]) ee = np.abs(ii_quad - ii_comp_quad) logEvent("hk=%f\t quad-int=%f\t comp-quad-int=%f error=%f" % (1.0 / N, ii_quad, ii_comp_quad, ee)) return 1.0 / N, ee
def attachModel(self,model,ar): import copy self.model=model self.ar=ar self.writer = Archiver.XdmfWriter() self.nd = model.levelModelList[-1].nSpace_global m = self.model.levelModelList[-1] flagMax = max(m.mesh.elementBoundaryMaterialTypes) flagMin = min(m.mesh.elementBoundaryMaterialTypes) assert(flagMin == 0) assert(flagMax >= 0) self.nForces=flagMax+1 self.levelFlist=[] for m in self.model.levelModelList: if self.nd == 2: F = numpy.zeros((self.nForces,2),'d') elif self.nd == 3: F = numpy.zeros((self.nForces,3),'d') else: logEvent("Can't use stress computation for nd = "+`self.nd`) F=None self.levelFlist.append(F) self.historyF=[] self.historyF.append(copy.deepcopy(self.levelFlist)) return self
def test_LinearADR_Sine(): logEvent("LinearADR_Sine") sol = AnalyticalSolutions.LinearADR_Sine() u = [sol.uOfX(x) for x in X] assert u[midpoint_x_index] == 0.22471248696198207 Du = [sol.duOfX(x)[0] for x in X] assert Du[midpoint_x_index] == 6.122493544431436 aflux = [sol.advectiveFluxOfX(x)[0] for x in X] assert aflux[midpoint_x_index] == 0.22471248696198207 dflux = [sol.diffusiveFluxOfX(x)[0] for x in X] assert dflux[midpoint_x_index] == -0.061224935444314364 tflux = [sol.totalFluxOfX(x)[0] for x in X] assert tflux[midpoint_x_index] == 0.1634875515176677 r = [sol.rOfUX(sol.uOfX(x), x) for x in X] assert r[midpoint_x_index] == -6.211206478443425 if save_plots: fig = plt.figure() plt.title("LinearADR_Sine") plt.plot(Xx, u, label='Solution') plt.plot(Xx, Du, label='Gradient') plt.plot(Xx, aflux, label='Advective Flux') plt.plot(Xx, dflux, label='Diffusive Flux') plt.plot(Xx, tflux, label='Total Flux') plt.plot(Xx, r, label='reaction') plt.legend() plt.savefig("LinearADR_Sine.png")
def ex3(N, hk, r0): r""" Compute the integral of :math:`1_{|[x,y]|<= r0}` :math: `r0<=0.5*sqrt(2)` Parameters ---------- N : int Order of base quadrature rule hk : double submesh element diameter r0 : integrand parameter """ quad = Quadrature.GaussTriangle(N) comp_quad = Quadrature.CompositeTriangle(quad, hk) N = int(np.ceil(1 / hk)) ii = np.sum(comp_quad.weights[np.less_equal( comp_quad.points[:, 0] ** 2 + comp_quad.points[:, 1] ** 2, r0 * r0)]) ee = np.abs(ii - r0**2 * 0.25 * np.pi) logEvent("hk=%f\t true-int=%f\t comp-int=%f error=%f" % (1.0 / N, r0**2 * 0.25 * np.pi, ii, ee)) return 1.0 / N, ee
def ex3(N, hk, r0): r""" Compute the integral of :math:`1_{|[x,y]|<= r0}` :math: `r0<=0.5*sqrt(2)` Parameters ---------- N : int Order of base quadrature rule hk : double submesh element diameter r0 : integrand parameter """ quad = Quadrature.GaussTriangle(N) comp_quad = Quadrature.CompositeTriangle(quad, hk) N = int(np.ceil(old_div(1, hk))) ii = np.sum(comp_quad.weights[np.less_equal( comp_quad.points[:, 0]**2 + comp_quad.points[:, 1]**2, r0 * r0)]) ee = np.abs(ii - r0**2 * 0.25 * np.pi) logEvent("hk=%f\t true-int=%f\t comp-int=%f error=%f" % (old_div(1.0, N), r0**2 * 0.25 * np.pi, ii, ee)) return old_div(1.0, N), ee
def ex2(N, hk, x0, y0): r""" Compute the integral of :math:`1_{x0*y+y0*x<= x0*y0}` :math:`0\leqx0\leq1` and :math:`0\leqy0\leq1` Parameters ---------- N : int Order of base quadrature rule hk : double submesh element diameter x0 : integrand parameter y0 : integrand parameter """ quad = Quadrature.GaussTriangle(N) comp_quad = Quadrature.CompositeTriangle(quad, hk) N = int(np.ceil(1 / hk)) ii = np.sum(comp_quad.weights[np.less_equal( comp_quad.points[:, 0] * y0 + comp_quad.points[:, 1] * x0, x0 * y0)]) ee = np.abs(ii - x0 * y0 * 0.5) logEvent("hk=%f\t true-int=%f\t comp-int=%f error=%f" % (1.0 / N, x0 * y0 * 0.5, ii, ee)) return 1.0 / N, ee
def ex2(N, hk, x0=1, y0=1, z0=1): r""" Compute the integral of :math:`1_{x/x0+y/y0+z/z0<= 1}` :math:`0< x0\leq 1` and :math:`0< y0\leq 1` and :math:`0< z0\leq 1` Parameters ---------- N : int Order of base quadrature rule hk : double submesh element diameter x0 : integrand parameter y0 : integrand parameter z0 : integrand parameter """ quad = Quadrature.GaussTetrahedron(N) comp_quad = Quadrature.CompositeTetrahedron(quad, hk) ii = np.sum(comp_quad.weights[np.less_equal( old_div(comp_quad.points[:, 0], x0) + old_div(comp_quad.points[:, 1], y0) + old_div(+comp_quad.points[:, 2], z0), 1.0)]) ee = np.abs(ii - x0 * y0 * z0 / 6.0) logEvent("hk=%f\t true-int=%f\t comp-int=%f error=%f" % (comp_quad.h, x0 * y0 * z0 / 6.0, ii, ee)) return comp_quad.h, ee
def reconstructMesh(self,domain,mesh): if hasattr(domain,"AdaptManager") and not isinstance(domain,proteus.Domain.PUMIDomain) : logEvent("Reconstruct based on Proteus, convert PUMI mesh to Proteus") nd = domain.nd from scipy import spatial meshVertexTree = spatial.cKDTree(mesh.nodeArray) meshVertex2Model= [0]*mesh.nNodes_owned assert domain.vertices, "model vertices (domain.vertices) were not specified" assert domain.vertexFlags, "model classification (domain.vertexFlags) needs to be specified" for idx,vertex in enumerate(domain.vertices): if(nd==2 and len(vertex) == 2): #there might be a smarter way to do this vertex.append(0.0) #need to make a 3D coordinate closestVertex = meshVertexTree.query(vertex) meshVertex2Model[closestVertex[1]] = 1 isModelVert = numpy.asarray(meshVertex2Model).astype("i") meshBoundaryConnectivity = numpy.zeros((mesh.nExteriorElementBoundaries_global,2+nd),dtype=numpy.int32) for elementBdyIdx in range(len(mesh.exteriorElementBoundariesArray)): exteriorIdx = mesh.exteriorElementBoundariesArray[elementBdyIdx] meshBoundaryConnectivity[elementBdyIdx][0] = mesh.elementBoundaryMaterialTypes[exteriorIdx] meshBoundaryConnectivity[elementBdyIdx][1] = mesh.elementBoundaryElementsArray[exteriorIdx][0] meshBoundaryConnectivity[elementBdyIdx][2] = mesh.elementBoundaryNodesArray[exteriorIdx][0] meshBoundaryConnectivity[elementBdyIdx][3] = mesh.elementBoundaryNodesArray[exteriorIdx][1] if(nd==3): meshBoundaryConnectivity[elementBdyIdx][4] = mesh.elementBoundaryNodesArray[exteriorIdx][2] domain.AdaptManager.PUMIAdapter.reconstructFromProteus2(mesh.cmesh,isModelVert,meshBoundaryConnectivity)
def ex2(N, hk, x0=1, y0=1, z0=1): r""" Compute the integral of :math:`1_{x/x0+y/y0+z/z0<= 1}` :math:`0< x0\leq 1` and :math:`0< y0\leq 1` and :math:`0< z0\leq 1` Parameters ---------- N : int Order of base quadrature rule hk : double submesh element diameter x0 : integrand parameter y0 : integrand parameter z0 : integrand parameter """ quad = Quadrature.GaussTetrahedron(N) comp_quad = Quadrature.CompositeTetrahedron(quad, hk) ii = np.sum(comp_quad.weights[np.less_equal( comp_quad.points[:, 0] / x0 + comp_quad.points[:, 1] / y0 + + comp_quad.points[:, 2] / z0, 1.0)]) ee = np.abs(ii - x0 * y0 * z0 / 6.0) logEvent("hk=%f\t true-int=%f\t comp-int=%f error=%f" % (comp_quad.h, x0 * y0 * z0 / 6.0, ii, ee)) return comp_quad.h, ee
def ex6(N, hk): r""" Compute the integral of :math:`x*y*z` over the reference triangle Parameters ---------- N : int Order of base quadrature rule hk : double submesh element diameter """ quad = Quadrature.GaussTetrahedron(N) comp_quad = Quadrature.CompositeTetrahedron(quad, hk) quad_points = np.asarray(quad.points, 'd') quad_weights = np.asarray(quad.weights, 'd') ii_quad = np.sum( quad_weights * quad_points[:, 0] * quad_points[:, 1] * quad_points[:, 2]) ii_comp_quad = np.sum(comp_quad.weights * comp_quad.points[:, 0] * comp_quad.points[:, 1] * comp_quad.points[:, 2]) ee = np.abs(ii_quad - ii_comp_quad) logEvent("hk=%f\t quad-int=%f\t comp-quad-int=%f error=%f" % (comp_quad.h, ii_quad, ii_comp_quad, ee)) return comp_quad.h, ee
def ex4(N, hk): r""" Compute the integral of :math:`x` over the reference triangle Parameters ---------- N : int Order of base quadrature rule hk : double submesh element diameter """ quad = Quadrature.GaussTetrahedron(N) comp_quad = Quadrature.CompositeTetrahedron(quad, hk) quad_points = np.asarray(quad.points, 'd') quad_weights = np.asarray(quad.weights, 'd') ii_quad = np.sum(quad_weights * quad_points[:, 0]) ii_comp_quad = np.sum(comp_quad.weights * comp_quad.points[:, 0]) ee = np.abs(ii_quad - ii_comp_quad) logEvent("hk=%f\t quad-int=%f\t comp-quad-int=%f error=%f" % (comp_quad.h, ii_quad, ii_comp_quad, ee)) return comp_quad.h, ee
def ex2(N, hk, x0, y0): r""" Compute the integral of :math:`1_{x0*y+y0*x<= x0*y0}` :math:`0\leqx0\leq1` and :math:`0\leqy0\leq1` Parameters ---------- N : int Order of base quadrature rule hk : double submesh element diameter x0 : integrand parameter y0 : integrand parameter """ quad = Quadrature.GaussTriangle(N) comp_quad = Quadrature.CompositeTriangle(quad, hk) N = int(np.ceil(old_div(1, hk))) ii = np.sum(comp_quad.weights[np.less_equal( comp_quad.points[:, 0] * y0 + comp_quad.points[:, 1] * x0, x0 * y0)]) ee = np.abs(ii - x0 * y0 * 0.5) logEvent("hk=%f\t true-int=%f\t comp-int=%f error=%f" % (old_div(1.0, N), x0 * y0 * 0.5, ii, ee)) return old_div(1.0, N), ee
def PUMI_reallocate(self, mesh): p0 = self.pList[0] n0 = self.nList[0] if self.TwoPhaseFlow: nLevels = p0.myTpFlowProblem.general['nLevels'] nLayersOfOverlapForParallel = p0.myTpFlowProblem.general[ 'nLayersOfOverlapForParallel'] parallelPartitioningType = MeshTools.MeshParallelPartitioningTypes.element domain = p0.myTpFlowProblem.domain domain.MeshOptions.setParallelPartitioningType('element') else: nLevels = n0.nLevels nLayersOfOverlapForParallel = n0.nLayersOfOverlapForParallel parallelPartitioningType = n0.parallelPartitioningType domain = p0.domain logEvent("Generating %i-level mesh from PUMI mesh" % (nLevels, )) if domain.nd == 3: mlMesh = MeshTools.MultilevelTetrahedralMesh( 0, 0, 0, skipInit=True, nLayersOfOverlap=nLayersOfOverlapForParallel, parallelPartitioningType=parallelPartitioningType) if domain.nd == 2: mlMesh = MeshTools.MultilevelTriangularMesh( 0, 0, 0, skipInit=True, nLayersOfOverlap=nLayersOfOverlapForParallel, parallelPartitioningType=parallelPartitioningType) if self.comm.size() == 1: mlMesh.generateFromExistingCoarseMesh( mesh, nLevels, nLayersOfOverlap=nLayersOfOverlapForParallel, parallelPartitioningType=parallelPartitioningType) else: mlMesh.generatePartitionedMeshFromPUMI( mesh, nLevels, nLayersOfOverlap=nLayersOfOverlapForParallel) self.mlMesh_nList = [] for p in self.pList: self.mlMesh_nList.append(mlMesh) if (domain.PUMIMesh.size_field_config() == "isotropicProteus"): mlMesh.meshList[0].subdomainMesh.size_field = numpy.ones( (mlMesh.meshList[0].subdomainMesh.nNodes_global, 1), 'd') * 1.0e-1 if (domain.PUMIMesh.size_field_config() == 'anisotropicProteus'): mlMesh.meshList[0].subdomainMesh.size_scale = numpy.ones( (mlMesh.meshList[0].subdomainMesh.nNodes_global, 3), 'd') mlMesh.meshList[0].subdomainMesh.size_frame = numpy.ones( (mlMesh.meshList[0].subdomainMesh.nNodes_global, 9), 'd') #may want to trigger garbage collection here self.modelListOld = self.modelList logEvent("Allocating models on new mesh") self.allocateModels()
def test_LinearADR_Decay_DiracIC(): logEvent("LinearADR_Decay_DiracIC") sol = AnalyticalSolutions.LinearADR_Decay_DiracIC() up25 = [sol.uOfXT(x, T=0.25) for x in X] assert up25[midpoint_x_index] == 0.0045216528018377404 up75 = [sol.uOfXT(x, T=0.75) for x in X] assert up75[midpoint_x_index] == 6.435494248102993e-09 Dup25 = [sol.duOfXT(x, T=0.25)[0] for x in X] assert Dup25[midpoint_x_index] == -0.19346149763373902 Dup75 = [sol.duOfXT(x, T=0.75)[0] for x in X] assert Dup75[midpoint_x_index] == -3.062985739327577e-07 afluxp25 = [sol.advectiveFluxOfXT(x, T=0.25)[0] for x in X] assert afluxp25[midpoint_x_index] == 0.0045216528018377404 afluxp75 = [sol.advectiveFluxOfXT(x, T=0.75)[0] for x in X] assert afluxp75[midpoint_x_index] == 6.435494248102993e-09 dfluxp25 = [sol.diffusiveFluxOfXT(x, T=0.25)[0] for x in X] assert dfluxp25[midpoint_x_index] == 0.0019346149763373901 dfluxp75 = [sol.diffusiveFluxOfXT(x, T=0.75)[0] for x in X] assert dfluxp75[midpoint_x_index] == 3.062985739327577e-09 tfluxp25 = [sol.totalFluxOfXT(x, T=0.25)[0] for x in X] assert tfluxp25[midpoint_x_index] == 0.00645626777817513 tfluxp75 = [sol.totalFluxOfXT(x, T=0.75)[0] for x in X] assert tfluxp75[midpoint_x_index] == 9.498479987430571e-09 if save_plots: fig = plt.figure() plt.plot(Xx, up25, label='Solution,t=0.25') plt.plot(Xx, up75, label='Solution,t=0.75') plt.plot(Xx, Dup25, label='Gradient,t=0.25') plt.plot(Xx, Dup75, label='Gradient,t=0.75') plt.plot(Xx, afluxp25, label='Advective Flux,t=0.25') plt.plot(Xx, afluxp75, label='Advective Flux,t=0.75') plt.plot(Xx, dfluxp25, label='Diffusive Flux,t=0.25') plt.plot(Xx, dfluxp75, label='Diffusive Flux,t=0.75') plt.plot(Xx, tfluxp25, label='Total Flux,t=0.25') plt.plot(Xx, tfluxp75, label='Total Flux,t=0.75') plt.legend() plt.title("LinearADR_Decay_DiracIC.png") plt.savefig("LinearADR_Decay_DiracIC.png")
def test_LinearAD_DiracIC(): logEvent("LinearAD_DiracIC") sol = AnalyticalSolutions.LinearAD_DiracIC() up25 = [sol.uOfXT(x, T=0.25) for x in X] assert up25[midpoint_x_index] == 0.005805917122996999 up75 = [sol.uOfXT(x, T=0.75) for x in X] assert up75[midpoint_x_index] == 1.362394143014481e-08 Dup25 = [sol.duOfXT(x, T=0.25)[0] for x in X] assert Dup25[midpoint_x_index] == -0.24840948011219627 Dup75 = [sol.duOfXT(x, T=0.75)[0] for x in X] assert Dup75[midpoint_x_index] == -6.484340861040867e-07 afluxp25 = [sol.advectiveFluxOfXT(x, T=0.25)[0] for x in X] assert afluxp25[midpoint_x_index] == 0.005805917122996999 afluxp75 = [sol.advectiveFluxOfXT(x, T=0.75)[0] for x in X] assert afluxp75[midpoint_x_index] == 1.362394143014481e-08 dfluxp25 = [sol.diffusiveFluxOfXT(x, T=0.25)[0] for x in X] assert dfluxp25[midpoint_x_index] == 0.0024840948011219627 dfluxp75 = [sol.diffusiveFluxOfXT(x, T=0.75)[0] for x in X] assert dfluxp75[midpoint_x_index] == 6.484340861040867e-09 tfluxp25 = [sol.totalFluxOfXT(x, T=0.25)[0] for x in X] assert tfluxp25[midpoint_x_index] == 0.008290011924118962 tfluxp75 = [sol.totalFluxOfXT(x, T=0.75)[0] for x in X] assert tfluxp75[midpoint_x_index] == 2.0108282291185675e-08 if save_plots: fig = plt.figure() plt.plot(Xx, up25, label='Solution,t=0.25') plt.plot(Xx, up75, label='Solution,t=0.75') plt.plot(Xx, Dup25, label='Gradient,t=0.25') plt.plot(Xx, Dup75, label='Gradient,t=0.75') plt.plot(Xx, afluxp25, label='Advective Flux,t=0.25') plt.plot(Xx, afluxp75, label='Advective Flux,t=0.75') plt.plot(Xx, dfluxp25, label='Diffusive Flux,t=0.25') plt.plot(Xx, dfluxp75, label='Diffusive Flux,t=0.75') plt.plot(Xx, tfluxp25, label='Total Flux,t=0.25') plt.plot(Xx, tfluxp75, label='Total Flux,t=0.75') plt.legend() plt.title("LinearAD_DiracIC.png") plt.savefig("LinearAD_DiracIC.png")
def test_NonlinearADR_Decay_DiracIC(): logEvent("NonlinearADR_Decay_DiracIC") sol = AnalyticalSolutions.NonlinearADR_Decay_DiracIC() up25 = [sol.uOfXT(x, T=0.25) for x in X] assert up25[midpoint_x_index] == 0.0058003017280384575 up75 = [sol.uOfXT(x, T=0.75) for x in X] assert up75[midpoint_x_index] == 1.3623941337338921e-08 Dup25 = [sol.duOfXT(x, T=0.25)[0] for x in X] assert Dup25[midpoint_x_index] == -0.248169222231705570 Dup75 = [sol.duOfXT(x, T=0.75)[0] for x in X] assert Dup75[midpoint_x_index] == -6.484340816869727e-07 afluxp25 = [sol.advectiveFluxOfXT(x, T=0.25)[0] for x in X] assert afluxp25[midpoint_x_index] == 0.0058003017280384575 afluxp75 = [sol.advectiveFluxOfXT(x, T=0.75)[0] for x in X] assert afluxp75[midpoint_x_index] == 1.3623941337338921e-08 dfluxp25 = [sol.diffusiveFluxOfXT(x, T=0.25)[0] for x in X] assert dfluxp25[midpoint_x_index] == 0.0024816922223170556 dfluxp75 = [sol.diffusiveFluxOfXT(x, T=0.75)[0] for x in X] assert dfluxp75[midpoint_x_index] == 6.484340816869727e-09 tfluxp25 = [sol.totalFluxOfXT(x, T=0.25)[0] for x in X] assert tfluxp25[midpoint_x_index] == 0.008281993950355513 tfluxp75 = [sol.totalFluxOfXT(x, T=0.75)[0] for x in X] assert tfluxp75[midpoint_x_index] == 2.010828215420865e-08 if save_plots: fig = plt.figure() plt.plot(Xx, up25, label='Solution,t=0.25') plt.plot(Xx, up75, label='Solution,t=0.75') plt.plot(Xx, Dup25, label='Gradient,t=0.25') plt.plot(Xx, Dup75, label='Gradient,t=0.75') plt.plot(Xx, afluxp25, label='Advective Flux,t=0.25') plt.plot(Xx, afluxp75, label='Advective Flux,t=0.75') plt.plot(Xx, dfluxp25, label='Diffusive Flux,t=0.25') plt.plot(Xx, dfluxp75, label='Diffusive Flux,t=0.75') plt.plot(Xx, tfluxp25, label='Total Flux,t=0.25') plt.plot(Xx, tfluxp75, label='Total Flux,t=0.75') plt.legend() plt.title("NonlinearADR_Decay_DiracIC.png") plt.savefig("NonlinearADR_Decay_DiracIC.png")
def getJacobian(self, jacobian): cfemIntegrals.zeroJacobian_CSR(self.nNonzerosInJacobian, jacobian) self.addedMass.calculateJacobian( # element self.u[0].femSpace.elementMaps.psi, self.u[0].femSpace.elementMaps.grad_psi, self.mesh.nodeArray, self.mesh.elementNodesArray, self.elementQuadratureWeights[('u', 0)], self.u[0].femSpace.psi, self.u[0].femSpace.grad_psi, self.u[0].femSpace.psi, self.u[0].femSpace.grad_psi, # element boundary self.u[0].femSpace.elementMaps.psi_trace, self.u[0].femSpace.elementMaps.grad_psi_trace, self.elementBoundaryQuadratureWeights[('u', 0)], self.u[0].femSpace.psi_trace, self.u[0].femSpace.grad_psi_trace, self.u[0].femSpace.psi_trace, self.u[0].femSpace.grad_psi_trace, self.u[0].femSpace.elementMaps.boundaryNormals, self.u[0].femSpace.elementMaps.boundaryJacobians, self.mesh.nElements_global, self.u[0].femSpace.dofMap.l2g, self.u[0].dof, self.coefficients.q_rho, self.csrRowIndeces[(0, 0)], self.csrColumnOffsets[(0, 0)], jacobian, self.mesh.nExteriorElementBoundaries_global, self.mesh.exteriorElementBoundariesArray, self.mesh.elementBoundaryElementsArray, self.mesh.elementBoundaryLocalElementBoundariesArray, self.csrColumnOffsets_eb[(0, 0)]) for dofN in list(self.dirichletConditionsForceDOF[0]. DOFBoundaryConditionsDict.keys()): global_dofN = self.offset[0] + self.stride[0] * dofN self.nzval[numpy.where(self.colind == global_dofN)] = 0.0 # column self.nzval[self.rowptr[global_dofN]:self.rowptr[global_dofN + 1]] = 0.0 # row zeroRow = True for i in range(self.rowptr[global_dofN], self.rowptr[global_dofN + 1]): # row if (self.colind[i] == global_dofN): self.nzval[i] = 1.0 zeroRow = False if zeroRow: raise RuntimeError( "Jacobian has a zero row because sparse matrix has no diagonal entry at row " + repr(global_dofN) + ". You probably need add diagonal mass or reaction term") logEvent("Jacobian ", level=10, data=jacobian) self.nonlinear_function_jacobian_evaluations += 1 return jacobian
def test_LinearAD_SteadyState(): logEvent("AD_SteadyState") sol = AnalyticalSolutions.LinearAD_SteadyState() y = [sol.uOfX(x) for x in X] assert y[midpoint_x_index] == 0.9882908500750013 if save_plots: fig = plt.figure() plt.plot(Xx, y, label='Solution,q=1,r=1') plt.legend() plt.title("LinearAD_SteadyStage") plt.savefig("LinearAD_SteadyState.png")
def initialAdapt(self): if (hasattr(self.pList[0].domain.AdaptManager, 'PUMIAdapter') and self.pList[0].domain.AdaptManager.PUMIAdapter.adaptMesh() and (b"pseudo" in self.domain.AdaptManager.sizeInputs or b"interface" in self.domain.AdaptManager.sizeInputs or b"ibm" in self.domain.AdaptManager.sizeInputs) and self.so.useOneMesh and not self.opts.hotStart): self.PUMI_transferFields() logEvent("Initial Adapt before Solve") self.PUMI_adaptMesh(b"interface") self.PUMI_transferFields() logEvent("Initial Adapt 2 before Solve") self.PUMI_adaptMesh(b"interface")
def getJacobian(self, jacobian): cfemIntegrals.zeroJacobian_CSR(self.nNonzerosInJacobian, jacobian) self.addedMass.calculateJacobian( # element self.u[0].femSpace.elementMaps.psi, self.u[0].femSpace.elementMaps.grad_psi, self.mesh.nodeArray, self.mesh.elementNodesArray, self.elementQuadratureWeights[('u', 0)], self.u[0].femSpace.psi, self.u[0].femSpace.grad_psi, self.u[0].femSpace.psi, self.u[0].femSpace.grad_psi, # element boundary self.u[0].femSpace.elementMaps.psi_trace, self.u[0].femSpace.elementMaps.grad_psi_trace, self.elementBoundaryQuadratureWeights[('u', 0)], self.u[0].femSpace.psi_trace, self.u[0].femSpace.grad_psi_trace, self.u[0].femSpace.psi_trace, self.u[0].femSpace.grad_psi_trace, self.u[0].femSpace.elementMaps.boundaryNormals, self.u[0].femSpace.elementMaps.boundaryJacobians, self.mesh.nElements_global, self.u[0].femSpace.dofMap.l2g, self.u[0].dof, self.coefficients.q_rho, self.csrRowIndeces[(0, 0)], self.csrColumnOffsets[(0, 0)], jacobian, self.mesh.nExteriorElementBoundaries_global, self.mesh.exteriorElementBoundariesArray, self.mesh.elementBoundaryElementsArray, self.mesh.elementBoundaryLocalElementBoundariesArray, self.csrColumnOffsets_eb[(0, 0)]) for dofN in self.dirichletConditionsForceDOF[0].DOFBoundaryConditionsDict.keys(): global_dofN = self.offset[0] + self.stride[0] * dofN self.nzval[numpy.where(self.colind == global_dofN)] = 0.0 # column self.nzval[self.rowptr[global_dofN]:self.rowptr[global_dofN + 1]] = 0.0 # row zeroRow = True for i in range(self.rowptr[global_dofN], self.rowptr[global_dofN + 1]): # row if (self.colind[i] == global_dofN): self.nzval[i] = 1.0 zeroRow = False if zeroRow: raise RuntimeError("Jacobian has a zero row because sparse matrix has no diagonal entry at row " + `global_dofN`+". You probably need add diagonal mass or reaction term") logEvent("Jacobian ", level=10, data=jacobian) self.nonlinear_function_jacobian_evaluations += 1 return jacobian
def initialAdapt(self): if (hasattr(self.pList[0].domain, 'PUMIMesh') and self.pList[0].domain.PUMIMesh.adaptMesh() and (self.pList[0].domain.PUMIMesh.size_field_config() == b"combined" or self.pList[0].domain.PUMIMesh.size_field_config() == b"pseudo" or self.pList[0].domain.PUMIMesh.size_field_config() == b"isotropic") and self.so.useOneMesh and not self.opts.hotStart): self.PUMI_transferFields() logEvent("Initial Adapt before Solve") self.PUMI_adaptMesh(b"interface") self.PUMI_transferFields() logEvent("Initial Adapt 2 before Solve") self.PUMI_adaptMesh(b"interface")
def test_NonlinearAD_SteadyState(): logEvent("NonlinearAD_SteadyState") sol = AnalyticalSolutions.NonlinearAD_SteadyState(q=2, r=1) y = [sol.uOfX(x) for x in X] assert y[midpoint_x_index] == 0.9948469998751492 if save_plots: fig = plt.figure() plt.plot(Xx, y, label='Solution,q=2,r=1') sol = AnalyticalSolutions.NonlinearAD_SteadyState(q=1, r=2) y = [sol.uOfX(x) for x in X] assert y[midpoint_x_index] == 0.990588835252627 if save_plots: fig = plt.figure() plt.plot(Xx, [sol.uOfX(x) for x in X], label='Solution,q=1,r=2') plt.legend() plt.title("NonlinearAD_SteadyState") plt.savefig("NonlinearAD_SteadyState.png")
def PUMI_reallocate(self,mesh): p0 = self.pList[0] n0 = self.nList[0] nLevels = n0.nLevels nLayersOfOverlapForParallel = n0.nLayersOfOverlapForParallel parallelPartitioningType = MeshTools.MeshParallelPartitioningTypes.element domain = p0.domain domain.MeshOptions.setParallelPartitioningType('element') logEvent("Generating %i-level mesh from PUMI mesh" % (nLevels,)) if domain.nd == 3: mlMesh = MeshTools.MultilevelTetrahedralMesh( 0,0,0,skipInit=True, nLayersOfOverlap=nLayersOfOverlapForParallel, parallelPartitioningType=parallelPartitioningType) if domain.nd == 2: mlMesh = MeshTools.MultilevelTriangularMesh( 0,0,0,skipInit=True, nLayersOfOverlap=nLayersOfOverlapForParallel, parallelPartitioningType=parallelPartitioningType) if self.comm.size()==1: mlMesh.generateFromExistingCoarseMesh( mesh,nLevels, nLayersOfOverlap=nLayersOfOverlapForParallel, parallelPartitioningType=parallelPartitioningType) else: mlMesh.generatePartitionedMeshFromPUMI( mesh,nLevels, nLayersOfOverlap=nLayersOfOverlapForParallel) #need to remove old mlMesh references to ensure the number of mesh entities is properly updated self.mlMesh_nList.clear() for p in self.pList: self.mlMesh_nList.append(mlMesh) if (b"isotropicProteus" in self.domain.AdaptManager.sizeInputs): mlMesh.meshList[0].subdomainMesh.size_field = numpy.ones((mlMesh.meshList[0].subdomainMesh.nNodes_global,1),'d')*1.0e-1 if (b'anisotropicProteus' in self.domain.AdaptManager.sizeInputs): mlMesh.meshList[0].subdomainMesh.size_scale = numpy.ones((mlMesh.meshList[0].subdomainMesh.nNodes_global,3),'d') mlMesh.meshList[0].subdomainMesh.size_frame = numpy.ones((mlMesh.meshList[0].subdomainMesh.nNodes_global,9),'d') #may want to trigger garbage collection here self.modelListOld = self.modelList logEvent("Allocating models on new mesh") self.allocateModels()
def preStep(self, t, firstStep=False): logEvent("Updating area function scaling coefficient and quadrature", level=3) # careful for nodeArray0 if mesh was moved with another moving mesh model self.mesh.nodeArray0[:] = self.mesh.nodeArray[:] self.mesh.elementBoundaryNormalsArray0[:] = self.mesh.elementBoundaryNormalsArray[:] self.evaluateFunAtQuadraturePoints() self.cCoefficients.preStep() self.C = self.cCoefficients.C self.model.areas = self.areas if self.ntimes_i == 0: self.mesh.nodeArray0[:] = self.mesh.nodeArray[:] logEvent("Finished updating area function", level=3) if self.t != self.model.t_mesh: self.nt += 1 self.t_last = self.t self.t = self.model.t_mesh self.poststepdone = False if self.resetNodeVelocityArray is True and self.ntimes_i == 0: self.mesh.nodeVelocityArray[:] = 0.
def hotstartWithPUMI(self): #Call restart functions logEvent("Converting PUMI mesh to Proteus") if self.pList[0].domain.nd == 3: mesh = MeshTools.TetrahedralMesh() else: mesh = MeshTools.TriangularMesh() mesh.convertFromPUMI(self.pList[0].domain.AdaptManager.PUMIAdapter, self.pList[0].domain.faceList, self.pList[0].domain.regList, parallel = self.comm.size() > 1, dim = self.pList[0].domain.nd) if(self.pList[0].domain.checkpointInfo==None): sys.exit("Need to specify checkpointInfo file in inputs") else: self.PUMIcheckpointer.DecodeModel(self.pList[0].domain.checkpointInfo) self.PUMI_reallocate(mesh) #need to double check if this call is necessaryor if it can be simplified to a shorter call PUMI2Proteus(self,self.pList[0].domain)
def PUMI_adaptMesh(self,inputString=b""): """ Uses a computed error field to construct a size field and adapts the mesh using SCOREC tools (a.k.a. MeshAdapt) """ ## domain = self.domain if(hasattr(self,"nSolveSteps")): logEvent("h-adapt mesh by calling AdaptAdaptManager.PUMIAdapter at step %s" % self.nSolveSteps) if(b"pseudo" in self.domain.AdaptManager.sizeInputs): logEvent("Testing solution transfer and restart feature of adaptation. No actual mesh adaptation!") else: domain.AdaptManager.PUMIAdapter.adaptPUMIMesh(inputString) logEvent("Converting PUMI mesh to Proteus") #ibaned: PUMI conversion #2 #TODO: this code is nearly identical to #PUMI conversion #1, they should be merged #into a function if domain.nd == 3: mesh = MeshTools.TetrahedralMesh() else: mesh = MeshTools.TriangularMesh() mesh.convertFromPUMI(domain, domain.AdaptManager.PUMIAdapter, domain.faceList, domain.regList, parallel = self.comm.size() > 1, dim = domain.nd) self.PUMI_reallocate(mesh) self.PUMI2Proteus(domain)
def preStep(self, t, firstStep=False): logEvent("MoveMesh preStep") self.model.preStep() for s in self.solidsList: logEvent("Calling step on solids") logEvent(repr(s)) s.step()
def calculateExteriorElementBoundaryQuadrature(self): logEvent("initalizing ebqe vectors for post-procesing velocity") self.u[0].femSpace.elementMaps.getValuesGlobalExteriorTrace(self.elementBoundaryQuadraturePoints, self.ebqe['x']) self.u[0].femSpace.elementMaps.getJacobianValuesGlobalExteriorTrace(self.elementBoundaryQuadraturePoints, self.ebqe['inverse(J)'], self.ebqe['g'], self.ebqe['sqrt(det(g))'], self.ebqe['n']) cfemIntegrals.calculateIntegrationWeights(self.ebqe['sqrt(det(g))'], self.elementBoundaryQuadratureWeights[('u', 0)], self.ebqe[('dS_u', 0)]) self.u[0].femSpace.elementMaps.getBasisValuesTraceRef( self.elementBoundaryQuadraturePoints) self.u[0].femSpace.elementMaps.getBasisGradientValuesTraceRef( self.elementBoundaryQuadraturePoints) self.u[0].femSpace.getBasisValuesTraceRef( self.elementBoundaryQuadraturePoints) self.u[0].femSpace.getBasisGradientValuesTraceRef( self.elementBoundaryQuadraturePoints) logEvent("initializing coefficients ebqe") self.coefficients.initializeGlobalExteriorElementBoundaryQuadrature(self.timeIntegration.t, self.ebqe)
def ex3(N, hk, r0): r""" Compute the integral of :math:`1_{|[x,y,z]|<= r0}` :math: `r0<=0.5*sqrt(2)` Parameters ---------- N : int Order of base quadrature rule hk : double submesh element diameter r0 : integrand parameter """ quad = Quadrature.GaussTetrahedron(N) comp_quad = Quadrature.CompositeTetrahedron(quad, hk) ii = np.sum(comp_quad.weights[np.less_equal( comp_quad.points[:, 0] ** 2 + comp_quad.points[:, 1] ** 2 + comp_quad.points[:, 2] ** 2, r0 * r0)]) ee = np.abs(ii - r0**3 * np.pi / 6.0) logEvent("hk=%f\t true-int=%f\t comp-int=%f error=%f" % (comp_quad.h, r0**3 * np.pi / 6.0, ii, ee)) return comp_quad.h, ee
def test_NonlinearDAE(): logEvent("Testing Solutions in 1D") logEvent("NonlinearDAE") from proteus.AnalyticalSolutions import NonlinearDAE sol = NonlinearDAE(5.0, 1.0) y1 = [sol.uOfT(x) for x in Xx] assert y1[midpoint_x_index] == 0.8349689658715417 sol = NonlinearDAE(5.0, 2.0) y2 = [sol.uOfT(x) for x in Xx] assert y2[midpoint_x_index] == 0.8471986417657046 sol = NonlinearDAE(5.0, 3.0) y3 = [sol.uOfT(x) for x in Xx] assert y3[midpoint_x_index] == 0.8572655778618113 sol = NonlinearDAE(5.0, 0.75) y075 = [sol.uOfT(x) for x in Xx] assert y075[midpoint_x_index] == 0.8314754625643243 sol = NonlinearDAE(5.0, 0.25) y025 = [sol.uOfT(x) for x in Xx] assert y025[midpoint_x_index] == 0.8238351907493889 sol = NonlinearDAE(5.0, -0.25) yn025 = [sol.uOfT(x) for x in Xx] assert yn025[midpoint_x_index] == 0.8151530579734992 sol = NonlinearDAE(5.0, -1.25) yn125 = [sol.uOfT(x) for x in Xx] assert yn125[midpoint_x_index] == 0.7934541671666694 if save_plots: fig = plt.figure() plt.plot(Xx, y1, label='Solution,q=1') plt.plot(Xx, y2, label='Solution,q=2') plt.plot(Xx, y3, label='Solution,q=3') plt.plot(Xx, y075, label='Solution,q=0.75') plt.plot(Xx, y025, label='Solution,q=0.25') plt.plot(Xx, yn025, label='Solution,q=-0.25') plt.plot(Xx, yn125, label='Solution,q=-1.25') plt.legend() plt.title("NonlinearDAE") plt.savefig("NonlinearDAE.png")
def test_line(self): M = 10 #====================================================================== # example 5: straight line #====================================================================== cell_size = np.zeros((M, ), 'd') error = np.zeros((M, ), 'd') convergence_rate = np.zeros((M, ), 'd') for i in range(M): cell_size[i], error[i] = ex2(1, old_div(1.0, 2**i), 0.6, 1.0) get_convergence_rate(cell_size, error, convergence_rate) logEvent("average convergence rate is %f" % np.average(convergence_rate[1:])) self.assertGreater(np.average(convergence_rate[1:]), 1.0, "convergence should be > 1") for i in range(M): cell_size[i], error[i] = ex2(2, old_div(1.0, 2**i), 0.6, 1.0) get_convergence_rate(cell_size, error, convergence_rate) logEvent("average convergence rate is %f" % np.average(convergence_rate[1:])) self.assertGreater(np.average(convergence_rate[1:]), 1.0, "convergence should be > 1") for i in range(M): cell_size[i], error[i] = ex2(3, old_div(1.0, 2**i), 0.6, 1.0) get_convergence_rate(cell_size, error, convergence_rate) logEvent("average convergence rate is %f" % np.average(convergence_rate[1:])) self.assertGreater(np.average(convergence_rate[1:]), 1.0, "convergence should be > 1") for i in range(M): cell_size[i], error[i] = ex2(4, old_div(1.0, 2**i), 0.6, 1.0) get_convergence_rate(cell_size, error, convergence_rate) logEvent("average convergence rate is %f" % np.average(convergence_rate[1:])) self.assertGreater(np.average(convergence_rate[1:]), 1.0, "convergence should be > 1")
def test_plane(self): M = 5 #====================================================================== # example 5: plane #====================================================================== cell_size = np.zeros((M,), 'd') error = np.zeros((M,), 'd') convergence_rate = np.zeros((M,), 'd') for i in range(M): cell_size[i], error[i] = ex2(1, 1.0 / 2**i, 0.5, 0.6, 0.7) get_convergence_rate(cell_size, error, convergence_rate) logEvent("average convergence rate is %f" % np.average(convergence_rate[1:])) self.assertGreater(np.average( convergence_rate[1:]), 1.0, "convergence should be > 1") for i in range(M): cell_size[i], error[i] = ex2(2, 1.0 / 2**i, 0.5, 0.6, 0.7) get_convergence_rate(cell_size, error, convergence_rate) logEvent("average convergence rate is %f" % np.average(convergence_rate[1:])) self.assertGreater(np.average( convergence_rate[1:]), 1.0, "convergence should be > 1") for i in range(M): cell_size[i], error[i] = ex2(3, 1.0 / 2**i, 0.5, 0.6, 0.7) get_convergence_rate(cell_size, error, convergence_rate) logEvent("average convergence rate is %f" % np.average(convergence_rate[1:])) self.assertGreater(np.average( convergence_rate[1:]), 1.0, "convergence should be > 1") for i in range(M): cell_size[i], error[i] = ex2(4, 1.0 / 2**i, 0.5, 0.6, 0.7) get_convergence_rate(cell_size, error, convergence_rate) logEvent("average convergence rate is %f" % np.average(convergence_rate[1:])) self.assertGreater(np.average( convergence_rate[1:]), 1.0, "convergence should be > 1")
def test_circle(self): M = 10 #====================================================================== # example 6: circle #====================================================================== cell_size = np.zeros((M,), 'd') error = np.zeros((M,), 'd') convergence_rate = np.zeros((M,), 'd') for i in range(M): cell_size[i], error[i] = ex3(1, 1.0 / 2**i, 0.5) get_convergence_rate(cell_size, error, convergence_rate) logEvent("average convergence rate is %f" % np.average(convergence_rate[1:])) self.assertGreater(np.average( convergence_rate[1:]), 1.0, "convergence should be > 1") for i in range(M): cell_size[i], error[i] = ex3(2, 1.0 / 2**i, 0.5) get_convergence_rate(cell_size, error, convergence_rate) logEvent("average convergence rate is %f" % np.average(convergence_rate[1:])) self.assertGreater(np.average( convergence_rate[1:]), 1.0, "convergence should be > 1") for i in range(M): cell_size[i], error[i] = ex3(3, 1.0 / 2**i, 0.5) get_convergence_rate(cell_size, error, convergence_rate) logEvent("average convergence rate is %f" % np.average(convergence_rate[1:])) self.assertGreater(np.average( convergence_rate[1:]), 1.0, "convergence should be > 1") for i in range(M): cell_size[i], error[i] = ex3(4, 1.0 / 2**i, 0.5) get_convergence_rate(cell_size, error, convergence_rate) logEvent("average convergence rate is %f" % np.average(convergence_rate[1:])) self.assertGreater(np.average( convergence_rate[1:]), 1.0, "convergence should be > 1")
def test_sphere(self): M = 5 #====================================================================== # example 6: circle #====================================================================== cell_size = np.zeros((M, ), 'd') error = np.zeros((M, ), 'd') convergence_rate = np.zeros((M, ), 'd') for i in range(M): cell_size[i], error[i] = ex3(1, old_div(1.0, 2**i), 0.5) get_convergence_rate(cell_size, error, convergence_rate) logEvent("average convergence rate is %f" % np.average(convergence_rate[1:])) self.assertGreater(np.average(convergence_rate[1:]), 1.0, "convergence should be > 1") for i in range(M): cell_size[i], error[i] = ex3(2, old_div(1.0, 2**i), 0.5) get_convergence_rate(cell_size, error, convergence_rate) logEvent("average convergence rate is %f" % np.average(convergence_rate[1:])) self.assertGreater(np.average(convergence_rate[1:]), 1.0, "convergence should be > 1") for i in range(M): cell_size[i], error[i] = ex3(3, old_div(1.0, 2**i), 0.5) get_convergence_rate(cell_size, error, convergence_rate) logEvent("average convergence rate is %f" % np.average(convergence_rate[1:])) self.assertGreater(np.average(convergence_rate[1:]), 1.0, "convergence should be > 1") for i in range(M): cell_size[i], error[i] = ex3(4, old_div(1.0, 2**i), 0.5) get_convergence_rate(cell_size, error, convergence_rate) logEvent("average convergence rate is %f" % np.average(convergence_rate[1:])) self.assertGreater(np.average(convergence_rate[1:]), 1.0, "convergence should be > 1")
from proteus.Profiling import logEvent import os import sys comm = Comm.get() Profiling.procID = comm.rank() Profiling.logFile = sys.stdout Profiling.logLevel = 2 Profiling.verbose = False import numpy as np import numpy.testing as npt import unittest logEvent("Testing Composite quadrature rule") def ex2(N, hk, x0, y0): r""" Compute the integral of :math:`1_{x0*y+y0*x<= x0*y0}` :math:`0\leqx0\leq1` and :math:`0\leqy0\leq1` Parameters ---------- N : int Order of base quadrature rule hk : double submesh element diameter x0 : integrand parameter y0 : integrand parameter
def PUMI_estimateError(self): """ Estimate the error using the classical element residual method by Ainsworth and Oden and generates a corresponding error field. """ adaptMeshNow = False domain = self.domain if (hasattr(domain, 'AdaptManager') and domain.AdaptManager.PUMIAdapter.adaptMesh() and self.so.useOneMesh): #and #self.nSolveSteps%domain.AdaptManager.PUMIAdapter.numAdaptSteps()==0): if (b"isotropicProteus" in self.domain.AdaptManager.sizeInputs): domain.AdaptManager.PUMIAdapter.transferFieldToPUMI( "proteus_size", self.modelList[0].levelModelList[0].mesh.size_field) if (b'anisotropicProteus' in self.domain.AdaptManager.sizeInputs): #Insert a function to define the size_scale/size_frame fields here. #For a given vertex, the i-th size_scale is roughly the desired edge length along the i-th direction specified by the size_frame for i in range( len(self.modelList[0].levelModelList[0].mesh.size_scale )): self.modelList[0].levelModelList[0].mesh.size_scale[ i, 0] = 1e-1 self.modelList[0].levelModelList[0].mesh.size_scale[ i, 1] = (old_div( self.modelList[0].levelModelList[0].mesh.nodeArray[ i, 1], 0.584)) * 1e-1 for j in range(3): for k in range(3): if (j == k): self.modelList[0].levelModelList[ 0].mesh.size_frame[i, 3 * j + k] = 1.0 else: self.modelList[0].levelModelList[ 0].mesh.size_frame[i, 3 * j + k] = 0.0 self.modelList[0].levelModelList[0].mesh.size_scale domain.AdaptManager.PUMIAdapter.transferFieldToPUMI( "proteus_sizeScale", self.modelList[0].levelModelList[0].mesh.size_scale) domain.AdaptManager.PUMIAdapter.transferFieldToPUMI( "proteus_sizeFrame", self.modelList[0].levelModelList[0].mesh.size_frame) self.PUMI_transferFields() logEvent("Estimate Error") if (b"error_erm" in self.domain.AdaptManager.sizeInputs): errorTotal = domain.AdaptManager.PUMIAdapter.get_local_error() if (domain.AdaptManager.PUMIAdapter.willAdapt()): adaptMeshNow = True logEvent("Need to Adapt") if (b"error_vms" in self.domain.AdaptManager.sizeInputs): errorTotal = domain.AdaptManager.PUMIAdapter.get_VMS_error() if (domain.AdaptManager.PUMIAdapter.willAdapt()): adaptMeshNow = True logEvent("Need to Adapt") if (self.nSolveSteps <= 5 ): #the first few time steps are ignored for adaptivity adaptMeshNow = False if (b"interface" in self.domain.AdaptManager.sizeInputs or b"ibm" in self.domain.AdaptManager.sizeInputs): if (domain.AdaptManager.PUMIAdapter.willInterfaceAdapt()): adaptMeshNow = True logEvent("Need to Adapt") logEvent('numSolveSteps %f ' % self.nSolveSteps) if (b'meshQuality' in self.domain.AdaptManager.sizeInputs): minQual = domain.AdaptManager.PUMIAdapter.getMinimumQuality() logEvent('The quality is %f ' % (minQual**(1. / 3.))) #adaptMeshNow=True if (minQual**(1. / 3.) < 0.25): adaptMeshNow = True logEvent("Need to Adapt") if (self.auxiliaryVariables['rans2p'] [0].subcomponents[0].__class__.__name__ == 'ProtChBody'): sphereCoords = numpy.asarray( self.auxiliaryVariables['rans2p'] [0].subcomponents[0].position) domain.AdaptManager.PUMIAdapter.updateSphereCoordinates( sphereCoords) logEvent( "Updated the sphere coordinates %f %f %f" % (sphereCoords[0], sphereCoords[1], sphereCoords[2])) else: sys.exit( "Haven't been implemented code yet to cover this behavior." ) if (b'pseudo' in self.domain.AdaptManager.sizeInputs): adaptMeshNow = True #if not adapting need to return data structures to original form which was modified by PUMI_transferFields() if (adaptMeshNow == False): for m in self.modelList: for lm in m.levelModelList: lm.u[0].dof[:] = lm.u_store[0].dof return adaptMeshNow
holes.append(hull_center) domain = Domain.PiecewiseLinearComplexDomain(vertices=vertices, vertexFlags=vertexFlags, facets=facets, facetFlags=facetFlags, regions=regions, regionFlags=regionFlags, holes=holes) #go ahead and add a boundary tags member domain.boundaryTags = boundaryTags if vessel: domain.writePoly("mesh_"+vessel) else: domain.writePoly("meshNoVessel") triangleOptions="VApq1.35q12ena%e" % ((he**3)/6.0,) logEvent("""Mesh generated using: tetgen -%s %s""" % (triangleOptions,domain.polyfile+".poly")) restrictFineSolutionToAllMeshes=False parallelPartitioningType = MeshTools.MeshParallelPartitioningTypes.node nLayersOfOverlapForParallel = 0 quad_order = 3 #---------------------------------------------------- # Boundary conditions and other flags #---------------------------------------------------- openTop = True openSides = True openEnd = True smoothBottom = False smoothObstacle = False movingDomain=False
def getResidual(self, u, r): import pdb import copy from proteus.flcbdfWrappers import globalSum """ Calculate the element residuals and add in to the global residual """ r.fill(0.0) # Load the unknowns into the finite element dof for dofN, g in self.dirichletConditionsForceDOF[0].DOFBoundaryConditionsDict.iteritems(): # load the BC valu # Load the unknowns into the finite element dof u[self.offset[0] + self.stride[0] * dofN] = g(self.dirichletConditionsForceDOF[0].DOFBoundaryPointDict[dofN], self.timeIntegration.t) self.setUnknowns(u) self.Aij[:,:,self.added_mass_i]=0.0 self.addedMass.calculateResidual( # element self.u[0].femSpace.elementMaps.psi, self.u[0].femSpace.elementMaps.grad_psi, self.mesh.nodeArray, self.mesh.elementNodesArray, self.elementQuadratureWeights[('u', 0)], self.u[0].femSpace.psi, self.u[0].femSpace.grad_psi, self.u[0].femSpace.psi, self.u[0].femSpace.grad_psi, # element boundary self.u[0].femSpace.elementMaps.psi_trace, self.u[0].femSpace.elementMaps.grad_psi_trace, self.elementBoundaryQuadratureWeights[('u', 0)], self.u[0].femSpace.psi_trace, self.u[0].femSpace.grad_psi_trace, self.u[0].femSpace.psi_trace, self.u[0].femSpace.grad_psi_trace, self.u[0].femSpace.elementMaps.boundaryNormals, self.u[0].femSpace.elementMaps.boundaryJacobians, # physics self.mesh.nElements_global, self.mesh.nElementBoundaries_owned, self.u[0].femSpace.dofMap.l2g, self.u[0].dof, self.coefficients.q_rho, self.offset[0], self.stride[0], r, self.mesh.nExteriorElementBoundaries_global, self.mesh.exteriorElementBoundariesArray, self.mesh.elementBoundaryElementsArray, self.mesh.elementBoundaryLocalElementBoundariesArray, self.mesh.elementBoundaryMaterialTypes, self.Aij, self.added_mass_i, self.barycenters, self.flags_rigidbody) for k in range(self.Aij.shape[0]): for j in range(self.Aij.shape[2]): self.Aij[k,j,self.added_mass_i] = globalSum( self.Aij[k,j,self.added_mass_i]) for i,flag in enumerate(self.flags_rigidbody): if flag==1: numpy.set_printoptions(precision=2, linewidth=160) logEvent("Added Mass Tensor for rigid body i" + `i`) logEvent("Aij = \n"+str(self.Aij[i])) for dofN, g in self.dirichletConditionsForceDOF[0].DOFBoundaryConditionsDict.iteritems(): r[self.offset[0] + self.stride[0] * dofN] = self.u[0].dof[dofN] - \ g(self.dirichletConditionsForceDOF[0].DOFBoundaryPointDict[dofN], self.timeIntegration.t) logEvent("Global residual", level=9, data=r) self.nonlinear_function_evaluations += 1
def __init__(self, uDict, phiDict, testSpaceDict, matType, dofBoundaryConditionsDict, dofBoundaryConditionsSetterDict, coefficients, elementQuadrature, elementBoundaryQuadrature, fluxBoundaryConditionsDict=None, advectiveFluxBoundaryConditionsSetterDict=None, diffusiveFluxBoundaryConditionsSetterDictDict=None, stressTraceBoundaryConditionsSetterDict=None, stabilization=None, shockCapturing=None, conservativeFluxDict=None, numericalFluxType=None, TimeIntegrationClass=None, massLumping=False, reactionLumping=False, options=None, name='defaultName', reuse_trial_and_test_quadrature=True, sd=True, movingDomain=False, bdyNullSpace=True): self.bdyNullSpace = bdyNullSpace from proteus import Comm # # set the objects describing the method and boundary conditions # self.movingDomain = movingDomain self.tLast_mesh = None # self.name = name self.sd = sd self.Hess = False self.lowmem = True self.timeTerm = True # allow turning off the time derivative # self.lowmem=False self.testIsTrial = True self.phiTrialIsTrial = True self.u = uDict self.ua = {} # analytical solutions self.phi = phiDict self.dphi = {} self.matType = matType # mwf try to reuse test and trial information across components if # spaces are the same self.reuse_test_trial_quadrature = reuse_trial_and_test_quadrature # True#False if self.reuse_test_trial_quadrature: for ci in range(1, coefficients.nc): assert self.u[ci].femSpace.__class__.__name__ == self.u[ 0].femSpace.__class__.__name__, "to reuse_test_trial_quad all femSpaces must be the same!" # Simplicial Mesh # assume the same mesh for all components for now self.mesh = self.u[0].femSpace.mesh self.testSpace = testSpaceDict self.dirichletConditions = dofBoundaryConditionsDict # explicit Dirichlet conditions for now, no Dirichlet BC constraints self.dirichletNodeSetList = None self.coefficients = coefficients self.coefficients.initializeMesh(self.mesh) self.nc = self.coefficients.nc self.stabilization = stabilization self.shockCapturing = shockCapturing # no velocity post-processing for now self.conservativeFlux = conservativeFluxDict self.fluxBoundaryConditions = fluxBoundaryConditionsDict self.diffusiveFluxBoundaryConditionsSetterDictDict = diffusiveFluxBoundaryConditionsSetterDictDict # determine whether the stabilization term is nonlinear self.stabilizationIsNonlinear = False # cek come back if self.stabilization is not None: for ci in range(self.nc): if coefficients.mass.has_key(ci): for flag in coefficients.mass[ci].values(): if flag == 'nonlinear': self.stabilizationIsNonlinear = True if coefficients.advection.has_key(ci): for flag in coefficients.advection[ci].values(): if flag == 'nonlinear': self.stabilizationIsNonlinear = True if coefficients.diffusion.has_key(ci): for diffusionDict in coefficients.diffusion[ci].values(): for flag in diffusionDict.values(): if flag != 'constant': self.stabilizationIsNonlinear = True if coefficients.potential.has_key(ci): for flag in coefficients.potential[ci].values(): if flag == 'nonlinear': self.stabilizationIsNonlinear = True if coefficients.reaction.has_key(ci): for flag in coefficients.reaction[ci].values(): if flag == 'nonlinear': self.stabilizationIsNonlinear = True if coefficients.hamiltonian.has_key(ci): for flag in coefficients.hamiltonian[ci].values(): if flag == 'nonlinear': self.stabilizationIsNonlinear = True # determine if we need element boundary storage self.elementBoundaryIntegrals = {} for ci in range(self.nc): self.elementBoundaryIntegrals[ci] = ( (self.conservativeFlux is not None) or ( numericalFluxType is not None) or ( self.fluxBoundaryConditions[ci] == 'outFlow') or ( self.fluxBoundaryConditions[ci] == 'mixedFlow') or ( self.fluxBoundaryConditions[ci] == 'setFlow')) # # calculate some dimensions # # assume same space dim for all variables self.nSpace_global = self.u[0].femSpace.nSpace_global self.nDOF_trial_element = [ u_j.femSpace.max_nDOF_element for u_j in self.u.values()] self.nDOF_phi_trial_element = [ phi_k.femSpace.max_nDOF_element for phi_k in self.phi.values()] self.n_phi_ip_element = [ phi_k.femSpace.referenceFiniteElement.interpolationConditions.nQuadraturePoints for phi_k in self.phi.values()] self.nDOF_test_element = [ femSpace.max_nDOF_element for femSpace in self.testSpace.values()] self.nFreeDOF_global = [ dc.nFreeDOF_global for dc in self.dirichletConditions.values()] self.nVDOF_element = sum(self.nDOF_trial_element) self.nFreeVDOF_global = sum(self.nFreeDOF_global) # NonlinearEquation.__init__(self, self.nFreeVDOF_global) # # build the quadrature point dictionaries from the input (this # is just for convenience so that the input doesn't have to be # complete) # elementQuadratureDict = {} elemQuadIsDict = isinstance(elementQuadrature, dict) if elemQuadIsDict: # set terms manually for I in self.coefficients.elementIntegralKeys: if elementQuadrature.has_key(I): elementQuadratureDict[I] = elementQuadrature[I] else: elementQuadratureDict[I] = elementQuadrature['default'] else: for I in self.coefficients.elementIntegralKeys: elementQuadratureDict[I] = elementQuadrature if self.stabilization is not None: for I in self.coefficients.elementIntegralKeys: if elemQuadIsDict: if elementQuadrature.has_key(I): elementQuadratureDict[ ('stab',) + I[1:]] = elementQuadrature[I] else: elementQuadratureDict[ ('stab',) + I[1:]] = elementQuadrature['default'] else: elementQuadratureDict[ ('stab',) + I[1:]] = elementQuadrature if self.shockCapturing is not None: for ci in self.shockCapturing.components: if elemQuadIsDict: if elementQuadrature.has_key(('numDiff', ci, ci)): elementQuadratureDict[('numDiff', ci, ci)] = elementQuadrature[ ('numDiff', ci, ci)] else: elementQuadratureDict[('numDiff', ci, ci)] = elementQuadrature[ 'default'] else: elementQuadratureDict[ ('numDiff', ci, ci)] = elementQuadrature if massLumping: for ci in self.coefficients.mass.keys(): elementQuadratureDict[('m', ci)] = Quadrature.SimplexLobattoQuadrature( self.nSpace_global, 1) for I in self.coefficients.elementIntegralKeys: elementQuadratureDict[ ('stab',) + I[1:]] = Quadrature.SimplexLobattoQuadrature(self.nSpace_global, 1) if reactionLumping: for ci in self.coefficients.mass.keys(): elementQuadratureDict[('r', ci)] = Quadrature.SimplexLobattoQuadrature( self.nSpace_global, 1) for I in self.coefficients.elementIntegralKeys: elementQuadratureDict[ ('stab',) + I[1:]] = Quadrature.SimplexLobattoQuadrature(self.nSpace_global, 1) elementBoundaryQuadratureDict = {} if isinstance(elementBoundaryQuadrature, dict): # set terms manually for I in self.coefficients.elementBoundaryIntegralKeys: if elementBoundaryQuadrature.has_key(I): elementBoundaryQuadratureDict[ I] = elementBoundaryQuadrature[I] else: elementBoundaryQuadratureDict[ I] = elementBoundaryQuadrature['default'] else: for I in self.coefficients.elementBoundaryIntegralKeys: elementBoundaryQuadratureDict[I] = elementBoundaryQuadrature # # find the union of all element quadrature points and # build a quadrature rule for each integral that has a # weight at each point in the union # mwf include tag telling me which indices are which quadrature rule? (self.elementQuadraturePoints, self.elementQuadratureWeights, self.elementQuadratureRuleIndeces) = Quadrature.buildUnion(elementQuadratureDict) self.nQuadraturePoints_element = self.elementQuadraturePoints.shape[0] self.nQuadraturePoints_global = self.nQuadraturePoints_element * \ self.mesh.nElements_global # # Repeat the same thing for the element boundary quadrature # (self.elementBoundaryQuadraturePoints, self.elementBoundaryQuadratureWeights, self.elementBoundaryQuadratureRuleIndeces) = Quadrature.buildUnion(elementBoundaryQuadratureDict) self.nElementBoundaryQuadraturePoints_elementBoundary = self.elementBoundaryQuadraturePoints.shape[ 0] self.nElementBoundaryQuadraturePoints_global = ( self.mesh.nElements_global * self.mesh.nElementBoundaries_element * self.nElementBoundaryQuadraturePoints_elementBoundary) if type(self.u[0].femSpace) == C0_AffineLinearOnSimplexWithNodalBasis: # print self.nQuadraturePoints_element if self.nSpace_global == 3: assert(self.nQuadraturePoints_element == 5) elif self.nSpace_global == 2: assert(self.nQuadraturePoints_element == 6) elif self.nSpace_global == 1: assert(self.nQuadraturePoints_element == 3) # print self.nElementBoundaryQuadraturePoints_elementBoundary if self.nSpace_global == 3: assert(self.nElementBoundaryQuadraturePoints_elementBoundary == 4) elif self.nSpace_global == 2: assert(self.nElementBoundaryQuadraturePoints_elementBoundary == 4) elif self.nSpace_global == 1: assert(self.nElementBoundaryQuadraturePoints_elementBoundary == 1) # # simplified allocations for test==trial and also check if space is mixed or not # self.added_mass_i = 0; self.Aij = np.zeros((self.coefficients.flags_rigidbody.shape[0], 6, 6), 'd') self.q = {} self.ebq = {} self.ebq_global = {} self.ebqe = {} self.phi_ip = {} # mesh #self.q['x'] = numpy.zeros((self.mesh.nElements_global,self.nQuadraturePoints_element,3),'d') self.ebqe['x'] = numpy.zeros( (self.mesh.nExteriorElementBoundaries_global, self.nElementBoundaryQuadraturePoints_elementBoundary, 3), 'd') self.q[('u', 0)] = numpy.zeros( (self.mesh.nElements_global, self.nQuadraturePoints_element), 'd') self.q[ ('grad(u)', 0)] = numpy.zeros( (self.mesh.nElements_global, self.nQuadraturePoints_element, self.nSpace_global), 'd') self.ebqe[ ('u', 0)] = numpy.zeros( (self.mesh.nExteriorElementBoundaries_global, self.nElementBoundaryQuadraturePoints_elementBoundary), 'd') self.ebqe[ ('grad(u)', 0)] = numpy.zeros( (self.mesh.nExteriorElementBoundaries_global, self.nElementBoundaryQuadraturePoints_elementBoundary, self.nSpace_global), 'd') self.q[('v', 0)] = numpy.zeros( (self.mesh.nElements_global, self.nQuadraturePoints_element, self.nDOF_trial_element[0]), 'd') self.q['J'] = numpy.zeros( (self.mesh.nElements_global, self.nQuadraturePoints_element, self.nSpace_global, self.nSpace_global), 'd') self.q['det(J)'] = numpy.zeros( (self.mesh.nElements_global, self.nQuadraturePoints_element), 'd') self.q['inverse(J)'] = numpy.zeros( (self.mesh.nElements_global, self.nQuadraturePoints_element, self.nSpace_global, self.nSpace_global), 'd') self.ebq[('v', 0)] = numpy.zeros( (self.mesh.nElements_global, self.mesh.nElementBoundaries_element, self.nElementBoundaryQuadraturePoints_elementBoundary, self.nDOF_trial_element[0]), 'd') self.ebq[('w', 0)] = numpy.zeros( (self.mesh.nElements_global, self.mesh.nElementBoundaries_element, self.nElementBoundaryQuadraturePoints_elementBoundary, self.nDOF_trial_element[0]), 'd') self.ebq['x'] = numpy.zeros( (self.mesh.nElements_global, self.mesh.nElementBoundaries_element, self.nElementBoundaryQuadraturePoints_elementBoundary, 3), 'd') self.ebq['hat(x)'] = numpy.zeros( (self.mesh.nElements_global, self.mesh.nElementBoundaries_element, self.nElementBoundaryQuadraturePoints_elementBoundary, 3), 'd') self.ebq['inverse(J)'] = numpy.zeros( (self.mesh.nElements_global, self.mesh.nElementBoundaries_element, self.nElementBoundaryQuadraturePoints_elementBoundary, self.nSpace_global, self.nSpace_global), 'd') self.ebq['g'] = numpy.zeros( (self.mesh.nElements_global, self.mesh.nElementBoundaries_element, self.nElementBoundaryQuadraturePoints_elementBoundary, self.nSpace_global - 1, self.nSpace_global - 1), 'd') self.ebq['sqrt(det(g))'] = numpy.zeros( (self.mesh.nElements_global, self.mesh.nElementBoundaries_element, self.nElementBoundaryQuadraturePoints_elementBoundary), 'd') self.ebq['n'] = numpy.zeros( (self.mesh.nElements_global, self.mesh.nElementBoundaries_element, self.nElementBoundaryQuadraturePoints_elementBoundary, self.nSpace_global), 'd') self.ebq[('dS_u', 0)] = numpy.zeros( (self.mesh.nElements_global, self.mesh.nElementBoundaries_element, self.nElementBoundaryQuadraturePoints_elementBoundary), 'd') self.ebqe['dS'] = numpy.zeros( (self.mesh.nExteriorElementBoundaries_global, self.nElementBoundaryQuadraturePoints_elementBoundary), 'd') self.ebqe[('dS_u', 0)] = self.ebqe['dS'] self.ebqe['n'] = numpy.zeros( (self.mesh.nExteriorElementBoundaries_global, self.nElementBoundaryQuadraturePoints_elementBoundary, self.nSpace_global), 'd') self.ebqe['inverse(J)'] = numpy.zeros( (self.mesh.nExteriorElementBoundaries_global, self.nElementBoundaryQuadraturePoints_elementBoundary, self.nSpace_global, self.nSpace_global), 'd') self.ebqe['g'] = numpy.zeros( (self.mesh.nExteriorElementBoundaries_global, self.nElementBoundaryQuadraturePoints_elementBoundary, self.nSpace_global - 1, self.nSpace_global - 1), 'd') self.ebqe['sqrt(det(g))'] = numpy.zeros( (self.mesh.nExteriorElementBoundaries_global, self.nElementBoundaryQuadraturePoints_elementBoundary), 'd') self.ebq_global['n'] = numpy.zeros( (self.mesh.nElementBoundaries_global, self.nElementBoundaryQuadraturePoints_elementBoundary, self.nSpace_global), 'd') self.ebq_global['x'] = numpy.zeros( (self.mesh.nElementBoundaries_global, self.nElementBoundaryQuadraturePoints_elementBoundary, 3), 'd') self.ebqe[('diffusiveFlux_bc_flag', 0, 0)] = numpy.zeros( (self.mesh.nExteriorElementBoundaries_global, self.nElementBoundaryQuadraturePoints_elementBoundary), 'i') self.ebqe[('diffusiveFlux_bc', 0, 0)] = numpy.zeros( (self.mesh.nExteriorElementBoundaries_global, self.nElementBoundaryQuadraturePoints_elementBoundary), 'd') self.ebqe[('diffusiveFlux', 0, 0)] = numpy.zeros((self.mesh.nExteriorElementBoundaries_global, self.nElementBoundaryQuadraturePoints_elementBoundary), 'd') self.points_elementBoundaryQuadrature = set() self.scalars_elementBoundaryQuadrature = set( [('u', ci) for ci in range(self.nc)]) self.vectors_elementBoundaryQuadrature = set() self.tensors_elementBoundaryQuadrature = set() logEvent(memory("element and element boundary Jacobians", "OneLevelTransport"), level=4) self.inflowBoundaryBC = {} self.inflowBoundaryBC_values = {} self.inflowFlux = {} for cj in range(self.nc): self.inflowBoundaryBC[cj] = numpy.zeros( (self.mesh.nExteriorElementBoundaries_global,), 'i') self.inflowBoundaryBC_values[cj] = numpy.zeros( (self.mesh.nExteriorElementBoundaries_global, self.nDOF_trial_element[cj]), 'd') self.inflowFlux[cj] = numpy.zeros( (self.mesh.nExteriorElementBoundaries_global, self.nElementBoundaryQuadraturePoints_elementBoundary), 'd') self.internalNodes = set(range(self.mesh.nNodes_global)) # identify the internal nodes this is ought to be in mesh # \todo move this to mesh for ebNE in range(self.mesh.nExteriorElementBoundaries_global): ebN = self.mesh.exteriorElementBoundariesArray[ebNE] eN_global = self.mesh.elementBoundaryElementsArray[ebN, 0] ebN_element = self.mesh.elementBoundaryLocalElementBoundariesArray[ ebN, 0] for i in range(self.mesh.nNodes_element): if i != ebN_element: I = self.mesh.elementNodesArray[eN_global, i] self.internalNodes -= set([I]) self.nNodes_internal = len(self.internalNodes) self.internalNodesArray = numpy.zeros((self.nNodes_internal,), 'i') for nI, n in enumerate(self.internalNodes): self.internalNodesArray[nI] = n # del self.internalNodes self.internalNodes = None logEvent("Updating local to global mappings", 2) self.updateLocal2Global() logEvent("Building time integration object", 2) logEvent(memory("inflowBC, internalNodes,updateLocal2Global", "OneLevelTransport"), level=4) # mwf for interpolating subgrid error for gradients etc if self.stabilization and self.stabilization.usesGradientStabilization: self.timeIntegration = TimeIntegrationClass( self, integrateInterpolationPoints=True) else: self.timeIntegration = TimeIntegrationClass(self) if options is not None: self.timeIntegration.setFromOptions(options) logEvent(memory("TimeIntegration", "OneLevelTransport"), level=4) logEvent("Calculating numerical quadrature formulas", 2) self.calculateQuadrature() self.setupFieldStrides() comm = Comm.get() self.comm = comm if comm.size() > 1: assert numericalFluxType is not None and numericalFluxType.useWeakDirichletConditions, "You must use a numerical flux to apply weak boundary conditions for parallel runs" logEvent(memory("stride+offset", "OneLevelTransport"), level=4) if numericalFluxType is not None: if options is None or options.periodicDirichletConditions is None: self.numericalFlux = numericalFluxType( self, dofBoundaryConditionsSetterDict, advectiveFluxBoundaryConditionsSetterDict, diffusiveFluxBoundaryConditionsSetterDictDict) else: self.numericalFlux = numericalFluxType( self, dofBoundaryConditionsSetterDict, advectiveFluxBoundaryConditionsSetterDict, diffusiveFluxBoundaryConditionsSetterDictDict, options.periodicDirichletConditions) else: self.numericalFlux = None # strong Dirichlet self.dirichletConditionsForceDOF = {0: DOFBoundaryConditions(self.u[cj].femSpace, dofBoundaryConditionsSetterDict[cj], weakDirichletConditions=False)} # set penalty terms # cek todo move into numerical flux initialization if self.ebq_global.has_key('penalty'): for ebN in range(self.mesh.nElementBoundaries_global): for k in range( self.nElementBoundaryQuadraturePoints_elementBoundary): self.ebq_global['penalty'][ebN, k] = self.numericalFlux.penalty_constant / ( self.mesh.elementBoundaryDiametersArray[ebN]**self.numericalFlux.penalty_power) # penalty term # cek move to Numerical flux initialization if self.ebqe.has_key('penalty'): for ebNE in range(self.mesh.nExteriorElementBoundaries_global): ebN = self.mesh.exteriorElementBoundariesArray[ebNE] for k in range( self.nElementBoundaryQuadraturePoints_elementBoundary): self.ebqe['penalty'][ebNE, k] = self.numericalFlux.penalty_constant / \ self.mesh.elementBoundaryDiametersArray[ebN]**self.numericalFlux.penalty_power logEvent(memory("numericalFlux", "OneLevelTransport"), level=4) self.elementEffectiveDiametersArray = self.mesh.elementInnerDiametersArray # use post processing tools to get conservative fluxes, None by default from proteus import PostProcessingTools self.velocityPostProcessor = PostProcessingTools.VelocityPostProcessingChooser( self) logEvent(memory("velocity postprocessor", "OneLevelTransport"), level=4) # helper for writing out data storage from proteus import Archiver self.elementQuadratureDictionaryWriter = Archiver.XdmfWriter() self.elementBoundaryQuadratureDictionaryWriter = Archiver.XdmfWriter() self.exteriorElementBoundaryQuadratureDictionaryWriter = Archiver.XdmfWriter() self.globalResidualDummy = None compKernelFlag = 0 self.addedMass = cAddedMass.AddedMass( self.nSpace_global, self.nQuadraturePoints_element, self.u[0].femSpace.elementMaps.localFunctionSpace.dim, self .u[0].femSpace.referenceFiniteElement.localFunctionSpace.dim, self.testSpace[0].referenceFiniteElement.localFunctionSpace.dim, self.nElementBoundaryQuadraturePoints_elementBoundary, compKernelFlag) self.barycenters = self.coefficients.barycenters self.flags_rigidbody = self.coefficients.flags_rigidbody
#================================================ # Print run data #================================================ logEvent(""" Reynolds number = %16.21e Froude number = %16.21e Hull Speed[M/S] = %16.21e Hull flow time[S] = %16.21e Wave length[M] = %16.21e Wave height[M] = %16.21e Wave angle[Rad] = %16.21e Wave periode[Hz] = %16.21e Wave velocity[M/S] = %16.21e T = %16.21e nDTout = %i """ % (Re, Fr, Um, residence_time, wave_length, wave_height, wave_angle, wave_periode, wave_vel_amp, T, nDTout)) # Discretization -- input options useOldPETSc=False useSuperlu = False # set to False if running in parallel with petsc.options
import unittest import numpy.testing as npt import numpy as np from subprocess import check_call from proteus.Profiling import logEvent from proteus import Comm, Profiling from proteus import Domain from proteus import MeshTools from proteus import SpatialTools as st comm = Comm.init() Profiling.procID = comm.rank() logEvent("Testing Gmsh Mesh Conversion") class TestGMSH(unittest.TestCase): def test_gmsh_generation_2D(self): domain = Domain.PlanarStraightLineGraphDomain() domain.vertices = [[0., 0., 0.], [5., 0., 0.], [5., 5., 0.], [0., 5., 0.]] domain.segments = [[0, 1], [1, 2], [2, 3], [3, 0]] domain.facets = [[[0, 1, 2, 3]]] domain.writeGeo('gmsh_mesh_test_2D', he_max=0.1) gmsh_cmd = "gmsh {0:s} -v 10 -2 -o {1:s} -format msh".format(domain.geofile+".geo", domain.geofile+".msh") check_call(gmsh_cmd, shell=True) MeshTools.msh2simplex(domain.geofile, nd=2) with open('gmsh_mesh_test_2D.node', 'r') as nodefile: npt.assert_equal(nodefile.readline(), '3425 2 0 1\n') with open('gmsh_mesh_test_2D.edge', 'r') as edgefile: npt.assert_equal(edgefile.readline(), '10072 1\n')
boundaryTags['box_left'], boundaryTags['box_top']] domain = Domain.PiecewiseLinearComplexDomain(vertices=vertices, vertexFlags=vertexFlags, facets=facets, facetFlags=facetFlags, holes=holes) #go ahead and add a boundary tags member domain.boundaryTags = boundaryTags domain.writePoly("mesh") domain.writePLY("mesh") domain.writeAsymptote("mesh") triangleOptions="VApq1.25q12ena%e" % ((he**3)/6.0,) logEvent("""Mesh generated using: tetgen -%s %s""" % (triangleOptions,domain.polyfile+".poly")) # Time stepping T=6.00 dt_init =0.001 dt_fixed = 0.1/Refinement nDTout = int(round(T/dt_fixed)) # Numerical parameters ns_forceStrongDirichlet = False#True if useMetrics: ns_shockCapturingFactor = 0.9 ns_lag_shockCapturing = True ns_lag_subgridError = True ls_shockCapturingFactor = 0.9 ls_lag_shockCapturing = True ls_sc_uref = 1.0
def calculate(self): import pdb for m,F in zip(self.model.levelModelList,self.levelFlist): F.flat[:]=0.0 assert(self.nd ==3) print "----------------need to add force calculation-------------------------------" # cfemIntegrals.calculateExteriorElementBoundaryStress3D(m.mesh.elementBoundaryMaterialTypes, # m.mesh.exteriorElementBoundariesArray, # m.mesh.elementBoundaryElementsArray, # m.mesh.elementBoundaryLocalElementBoundariesArray, # m.ebqe[('u',0)],#pressure # m.ebqe[('velocity',1)],#mom_flux_vec_u #cek todo, need to add real momentum flux # m.ebqe[('velocity',2)],#mom_flux_vec_v # m.ebqe[('velocity',3)],#mom_flux_vec_w # m.ebqe[('dS_u',0)],#dS # m.ebqe[('n')], # F) logEvent("Force") logEvent(`F`) Ftot=F[0,:] for ib in range(1,self.nForces): Ftot+=F[ib,:] logEvent("Total force on all boundaries") logEvent(`Ftot`) logEvent("x Force " +`self.model.stepController.t_model`+" "+`F[-1,0]`) logEvent("y Force " +`self.model.stepController.t_model`+" "+`F[-1,1]`) logEvent("z Force " +`self.model.stepController.t_model`+" "+`F[-1,2]`) #assume moving in the x direction self.body.addForce((0.0,0.0,F[-1,1]))#constrain to vertical motion initially self.world.step(self.model.stepController.dt_model) #f = m a = m (v_new - v_old)/dt #f dt/m = v_new - v_old #v_new = v_old + f dt/m print "net acceleration====================",F[-1,2]/self.mass+g[2] self.velocity = (0.0, 0.0, self.last_velocity[2]+F[-1,2]*self.model.stepController.dt_model/self.mass+g[2]*self.model.stepController.dt_model) self.position = (self.last_position[0]+self.velocity[0]*self.model.stepController.dt_model, self.last_position[1]+self.velocity[1]*self.model.stepController.dt_model, self.last_position[2]+self.velocity[2]*self.model.stepController.dt_model) self.h = (self.velocity[0]*self.model.stepController.dt_model, self.velocity[1]*self.model.stepController.dt_model, self.velocity[2]*self.model.stepController.dt_model) #x,y,z = self.body.getPosition() #u,v,w = self.body.getLinearVel() #self.position=(x,y,z) #self.velocity=(u,v,w) #self.h = (self.velocity[0]*self.model.stepController.dt_model, # self.velocity[1]*self.model.stepController.dt_model, # self.velocity[2]*self.model.stepController.dt_model) print "%1.2fsec: pos=(%6.3f, %6.3f, %6.3f) vel=(%6.3f, %6.3f, %6.3f)" % \ (self.model.stepController.t_model, self.position[0], self.position[1], self.position[2], self.velocity[0],self.velocity[1],self.velocity[2]) print "%1.2fsec: last_pos=(%6.3f, %6.3f, %6.3f) last_vel=(%6.3f, %6.3f, %6.3f)" % \ (self.model.stepController.t_model, self.last_position[0], self.last_position[1], self.last_position[2], self.last_velocity[0],self.last_velocity[1],self.last_velocity[2]) self.h = (self.velocity[0]*self.model.stepController.dt_model, self.velocity[1]*self.model.stepController.dt_model, self.velocity[2]*self.model.stepController.dt_model) self.last_velocity=self.velocity self.last_position=self.position print "dt model in object ",self.model.stepController.dt_model