def bubblematerial(c=1, N=20, dt=0.05, gridpoints=100, plotoutput=True): """ Calculate first arrival times for a wave travelling through NicolasBubble using a wavefront method that is then interpolated onto a grid Args: c: baseline wave speed N: number of points to put on initial wavefront dt: timestep (the wavefront implementation uses forward Euler) gridpoints: number of points to resolve on the grid plotoutput: whether to display output Returns: A 2D array containing the first arrival times at the points on the grid """ bounds = [[0, 1], [0, 1]] # The x-axis and y-axis bounds for the domain npoints = [gridpoints, gridpoints] # The number of points to (eventually) resolve in the grid speed = NicolasBubble() if plotoutput: pom.output2dfn(bounds, speed, npoints, show=False) # plot the speed function slowness = lambda x: 1 / speed(x) gradslowness = prw.gradient(slowness, 1e-6) # A very crude numerical gradient # These two lines would initialise a plane wave entering the domain # x0 = np.vstack((np.linspace(0,1,N), np.zeros(N))).T # p0 = np.vstack((np.zeros(N), np.ones(N))).T # These three lines initialise a source angles = np.linspace(-1e-2, math.pi + 1e-2, N) p0 = np.vstack((np.cos(angles), np.sin(angles))).T x0 = np.array([0.5, 0]) + dt * p0 # Perform the wavefront tracking wfs, idxs = prw.wavefront(x0, p0, slowness, gradslowness, dt, 1.25 / c, 0.1) if plotoutput: erw.plotwavefront(wfs, idxs, bounds) # plot the wavefronts # Use SciPy's interpolation (which doesn't work well when there are multiple arrival times) # phasefn = interpolatephase(wfs, dt) # pom.output2dfn(bounds, phasefn, npoints, show=False, type='contour') # Home-brew interpolation: sp = pug.StructuredPoints(np.array(bounds).T, npoints) # Define the points onto which we're going to interpolate initialbox = [[0.4, 0], [0.6, 0.1]] # The vertices of a box that contain (some of) the first wave front pointinfo = prw.StructuredPointInfo( sp, sp.getPoints(initialbox)[0] ) # Obtain the indices of the points that are in the initial box h = np.max((sp.upper - sp.lower) / sp.npoints) # The (maximum) grid spacing _, phases = prw.nodesToDirsAndPhases( wfs, idxs, pointinfo, lookback=int(math.ceil(h / (c * dt))) ) # perform the interpolation firstphase = ( np.array([p[0] if len(p) > 0 else -1 for p in phases]) * dt ) # We only care about the first phase found per point # pom.image(firstphase, (M+1,M+1), np.array(bounds)) if plotoutput: pom.contour(pointinfo.points, firstphase, npoints) return firstphase.reshape(npoints)
def examplepic(n, k=20): origin = np.array([-0.2,-0.2]) bounds=np.array([[0,1],[0,1]],dtype='d') npoints=np.array([k * 20,k * 20], dtype=int) g = pcb.FourierHankel(origin, [0], k) pom.output2dfn(bounds, g.values, npoints, alpha=1.0, cmap=mp.cm.get_cmap('binary')) rt = PlaneWaveFromSourceRule(origin) mesh = tum.regularsquaremesh(n) pom.showmesh(mesh) etob = {} psp.Problem(mesh,k, None).populateBasis(etob, rt) pom.showdirections(mesh, etob) mp.show()
basisrule = pcb.planeWaveBases(2,k,11) #basisrule = pcbr.ReferenceBasisRule(pcbr.Dubiner(0)) mortarrule = pcbr.ReferenceBasisRule(pcbr.Legendre1D(1)) s = -1j*k #s = 0 #tracebc = [0,0] mc = psm.MortarComputation(problem, basisrule, mortarrule, nquad, pcp.HelmholtzSystem, pcp.HelmholtzBoundary, s) #sol = mc.solution(psi.BrutalSolver(np.complex), dovolumes=True) sol = mc.solution(psi.GMRESSolver('ctor'), dovolumes=True) #solfaked = mc.fakesolution(g, [s, 1]) #print sol.x #pos.standardoutput(sol, 20, bounds, npoints, 'squaremortar') pom.output2dsoln(bounds, sol, npoints, plotmesh = True, show = False) #pom.output2dsoln(bounds, solfaked, npoints, plotmesh = True, show = False) pom.output2dfn(bounds, g.values, npoints, show=False) #rectmesh = tum.regularrectmesh([0,0.5], [0,1.0], n/2, n) #rectbd = {1:ig, 2:ig, 3:ig, 4:ig} #rectprob = psp.Problem(rectmesh, k, rectbd) #rectcmp = psc.DirectComputation(rectprob, basisrule, nquad, pcp.HelmholtzSystem) #rectsol = rectcmp.solution() #pom.output2dsoln([[0,0.5],[0,1]],rectsol, npoints, plotmesh=True, show=False) mp.show() # #sold = psc.DirectComputation(problem, basisrule, nquad, pcp.HelmholtzSystem).solution() #pos.standardoutput(sold, 20, bounds, npoints, 'squaremortar', mploutput=True)
def showtruesoln(k, scale): S = harmonic1(scale) g = HarmonicDerived(k, S) bounds=np.array([[0,1],[0,1]],dtype='d') npoints=np.array([k * scale * 10,k * scale * 10], dtype=int) pom.output2dfn(bounds, g.values, npoints)
def show(self): pom.output2dfn(self.bounds, self, [self.nx,self.ny])