def test_triinterp_colinear(): # Tests interpolating inside a triangulation with horizontal colinear # points (refer also to the tests :func:`test_trifinder` ). # # These are not valid triangulations, but we try to deal with the # simplest violations (i. e. those handled by default TriFinder). # # Note that the LinearTriInterpolator and the CubicTriInterpolator with # kind='min_E' or 'geom' still pass a linear patch test. # We also test interpolation inside a flat triangle, by forcing # *tri_index* in a call to :meth:`_interpolate_multikeys`. delta = 0. # If +ve, triangulation is OK, if -ve triangulation invalid, # if zero have colinear points but should pass tests anyway. x0 = np.array([1.5, 0, 1, 2, 3, 1.5, 1.5]) y0 = np.array([-1, 0, 0, 0, 0, delta, 1]) # We test different affine transformations of the initial figure ; to # avoid issues related to round-off errors we only use integer # coefficients (otherwise the Triangulation might become invalid even with # delta == 0). transformations = [[1, 0], [0, 1], [1, 1], [1, 2], [-2, -1], [-2, 1]] for transformation in transformations: x_rot = transformation[0] * x0 + transformation[1] * y0 y_rot = -transformation[1] * x0 + transformation[0] * y0 (x, y) = (x_rot, y_rot) z = 1.23 * x - 4.79 * y triangles = [[0, 2, 1], [0, 3, 2], [0, 4, 3], [1, 2, 5], [2, 3, 5], [3, 4, 5], [1, 5, 6], [4, 6, 5]] triang = mtri.Triangulation(x, y, triangles) xs = np.linspace(np.min(triang.x), np.max(triang.x), 20) ys = np.linspace(np.min(triang.y), np.max(triang.y), 20) xs, ys = np.meshgrid(xs, ys) xs = xs.ravel() ys = ys.ravel() mask_out = (triang.get_trifinder()(xs, ys) == -1) zs_target = np.ma.array(1.23 * xs - 4.79 * ys, mask=mask_out) linear_interp = mtri.LinearTriInterpolator(triang, z) cubic_min_E = mtri.CubicTriInterpolator(triang, z) cubic_geom = mtri.CubicTriInterpolator(triang, z, kind='geom') for interp in (linear_interp, cubic_min_E, cubic_geom): zs = interp(xs, ys) assert_array_almost_equal(zs_target, zs) # Testing interpolation inside the flat triangle number 4: [2, 3, 5] # by imposing *tri_index* in a call to :meth:`_interpolate_multikeys` itri = 4 pt1 = triang.triangles[itri, 0] pt2 = triang.triangles[itri, 1] xs = np.linspace(triang.x[pt1], triang.x[pt2], 10) ys = np.linspace(triang.y[pt1], triang.y[pt2], 10) zs_target = 1.23 * xs - 4.79 * ys for interp in (linear_interp, cubic_min_E, cubic_geom): zs, = interp._interpolate_multikeys(xs, ys, tri_index=itri * np.ones(10, dtype=np.int32)) assert_array_almost_equal(zs_target, zs)
def interpolate_velocity(self, xi, yi, relative=False, magnitude=True): """Interpolate velocity at given points. Parameters ---------- xi, yi - array-like : x and y coordinates of interpolation points relative - Boolean : compute velocity relative to u_b if True magnitude - Boolean : return magnitude of vector if True Returns ------- u_xi, u_yi - array-like : interpolated velocity components mag(u_i) - array-like : magnitude of interpolated velocity """ interpolator_u_x = tri.CubicTriInterpolator( self.triang, self.data['u_x'].values, kind='geom') interpolator_u_y = tri.CubicTriInterpolator( self.triang, self.data['u_y'].values, kind='geom') u_xi = interpolator_u_x(xi, yi) u_yi = interpolator_u_y(xi, yi) if relative: u_xi -= self.u_b[1] # paraview bug, see further down u_yi -= self.u_b[0] if magnitude: return np.sqrt(np.square(u_xi) + np.square(u_yi)) else: return u_yi, u_xi # paraview bug: the transform filter does not swap the vector components
def addInterpolator(self, interpolation='cubic', kind='geom'): ''' Add interpolator Object to the vector field. Arguments: *interpolation: string. 'cubic' or 'linear' ''' self.interType = interpolation self.interKind = kind if self.interType == 'cubic': self.vx_i = tri.CubicTriInterpolator(self.triangulation, self.vx, kind=self.interKind) self.vy_i = tri.CubicTriInterpolator(self.triangulation, self.vy, kind=self.interKind) self.vz_i = tri.CubicTriInterpolator(self.triangulation, self.vz, kind=self.interKind) elif self.interType == 'linear': self.vx_i = tri.LinearTriInterpolator(self.triangulation, self.vx) self.vy_i = tri.LinearTriInterpolator(self.triangulation, self.vy) self.vz_i = tri.LinearTriInterpolator(self.triangulation, self.vz) else: raise ValueError('Interpolation must be "cubic" or "linear".')
def plot_two_hyperparms(result, param_x, param_y, pretty_name, negative=True, save=False): if negative: res = result.copy() res['mean_test_score'] = -res['mean_test_score'] else: res = result.copy() fig, ax = plt.subplots(1, 2, figsize=(15, 6)) X_axis = res[param_x].astype(float) Y_axis = res[param_y].astype(float) xg, yg = np.meshgrid(np.linspace(X_axis.min(), X_axis.max(), 100), np.linspace(Y_axis.min(), Y_axis.max(), 100)) triangles = tri.Triangulation(X_axis, Y_axis) tri_interp = tri.CubicTriInterpolator(triangles, res['mean_test_score']) zg = tri_interp(xg, yg) ax[0].contourf(xg, yg, zg, norm=plt.Normalize(vmax=res['mean_test_score'].max(), vmin=res['mean_test_score'].min()), cmap=plt.cm.terrain) tri_interp = tri.CubicTriInterpolator(triangles, res['mean_fit_time']) zg = tri_interp(xg, yg) ax[1].contourf(xg, yg, zg, norm=plt.Normalize(vmax=res['mean_fit_time'].max(), vmin=res['mean_fit_time'].min()), cmap=plt.cm.terrain) ax[0].set_xlabel(param_x.split('__')[-1].title(), fontsize=12) ax[1].set_xlabel(param_x.split('__')[-1].title(), fontsize=12) ax[0].set_ylabel(param_y.split('__')[-1].title(), fontsize=12) ax[1].set_ylabel(param_y.split('__')[-1].title(), fontsize=12) ax[0].set_title('Test Score', fontsize=14) ax[1].set_title('Fit Time', fontsize=14) fig.suptitle(f'{pretty_name}', fontsize=18) if save: plt.savefig('plots/' + save) plt.show()
def interpTri(triVerts, triInd): from matplotlib import pyplot as plt import matplotlib.pyplot as plt import matplotlib.tri as mtri import numpy as np x = triVerts[:, 0] y = triVerts[:, 1] triang = mtri.Triangulation(triVerts[:, 0], triVerts[:, 1], triInd) # Interpolate to regularly-spaced quad grid. z = np.cos(1.5 * x) * np.cos(1.5 * y) xi, yi = np.meshgrid(np.linspace(0, 3, 20), np.linspace(0, 3, 20)) interp_lin = mtri.LinearTriInterpolator(triang, z) zi_lin = interp_lin(xi, yi) interp_cubic_geom = mtri.CubicTriInterpolator(triang, z, kind='geom') zi_cubic_geom = interp_cubic_geom(xi, yi) interp_cubic_min_E = mtri.CubicTriInterpolator(triang, z, kind='min_E') zi_cubic_min_E = interp_cubic_min_E(xi, yi) # Set up the figure fig, axs = plt.subplots(nrows=2, ncols=2) axs = axs.flatten() # Plot the triangulation. axs[0].tricontourf(triang, z) axs[0].triplot(triang, 'ko-') axs[0].set_title('Triangular grid') # Plot linear interpolation to quad grid. axs[1].contourf(xi, yi, zi_lin) axs[1].plot(xi, yi, 'k-', lw=0.5, alpha=0.5) axs[1].plot(xi.T, yi.T, 'k-', lw=0.5, alpha=0.5) axs[1].set_title("Linear interpolation") # Plot cubic interpolation to quad grid, kind=geom axs[2].contourf(xi, yi, zi_cubic_geom) axs[2].plot(xi, yi, 'k-', lw=0.5, alpha=0.5) axs[2].plot(xi.T, yi.T, 'k-', lw=0.5, alpha=0.5) axs[2].set_title("Cubic interpolation,\nkind='geom'") # Plot cubic interpolation to quad grid, kind=min_E axs[3].contourf(xi, yi, zi_cubic_min_E) axs[3].plot(xi, yi, 'k-', lw=0.5, alpha=0.5) axs[3].plot(xi.T, yi.T, 'k-', lw=0.5, alpha=0.5) axs[3].set_title("Cubic interpolation,\nkind='min_E'") fig.tight_layout() plt.show()
def interpolateField(self,values,grid_x,grid_y,triangulation,method='cubic'): ''' helper function methode=linear,cubic (default) ''' if method=='cubic': itp=tri.CubicTriInterpolator(triangulation,values) elif method=='linear': itp=tri.LinearTriInterpolator(triangulation,values) else: itp=tri.CubicTriInterpolator(triangulation,values) zi_ma = itp(grid_x, grid_y) zi=zi_ma.filled(np.nan) return zi
def plotSolnAndGrad(self, plt, solVec, title=""): plt.set_title(title) # plt.set_xlabel('x',size=14,weight='bold') # plt.set_ylabel('y',size=14,weight='bold') plt.set_aspect('equal') plt.set_xlim(-0.1, 5.1) plt.set_ylim(-0.1, 1.2) xy = np.asarray(self.mesh.vertices) tci = tri.CubicTriInterpolator(self.mesh.dtri, solVec) (Ex, Ey) = tci.gradient(self.mesh.dtri.x, self.mesh.dtri.y) E_norm = np.sqrt(Ex**2 + Ey**2) vals = plt.tricontourf(self.mesh.dtri, solVec, cmap="jet") plt.quiver(self.mesh.dtri.x, self.mesh.dtri.y, -Ex / E_norm, -Ey / E_norm, units='xy', scale=20., zorder=3, color='blue', width=0.002, headwidth=2., headlength=2.) return vals
def visualize_wafer_2d(mini_wafer_map): data = mini_wafer_map X = data['x'].tolist() Y = data['y'].tolist() value = data['value'].tolist() X = np.array(X) Y = np.array(Y) Z = np.array(value) npts = len(X) # 현재 PT 개수 ngridx, ngridy = 300,300 # 보간하고자 하는 PT 개수 lv = 10 fig, ax = plt.subplots(nrows=1) # Create grid values first. xi = np.linspace(-135, 135, ngridx) yi = np.linspace(-135, 135, ngridy) # Linearly interpolate the data (x, y) on a grid defined by (xi, yi). triang = tri.Triangulation(X, Y) interpolator = tri.CubicTriInterpolator(triang, Z) # LinearTriInterpolator Xi, Yi = np.meshgrid(xi, yi) zi = interpolator(Xi, Yi) s = ax.contour(xi, yi, zi, levels=lv, linewidths=0.5, colors = 'k') colors = ['#990033','#CC0033','#FF3300','#FF6600','#FFFF00','#FFFF66','#FFFF99','#FFFFCC','#669933','#339900','#33CC00','#33FF00','#003399','#0033CC','#0033FF','#0066FF','#663399','#663399','#9900CC','#9933FF','#9900FF'] colors = list(reversed(colors)) cntr1 = ax.contourf(xi, yi, zi, levels=lv, cmap=matplotlib.colors.ListedColormap(colors)) fig.colorbar(cntr1, shrink=0.8, aspect=5) # legend fig.savefig('2d graph.png')
def interpolate(self, z, x, y, kind='linear'): """ Interpolate data in 'z' on current grid onto points 'x' and 'y' kind = 'linear', 'cubic', 'barycentric' (default), 'nearest' """ if kind == 'linear': self.build_tri_voronoi() F = tri.LinearTriInterpolator(self._triv, z) return F(x, y) elif kind == 'cubic': self.build_tri_voronoi() F = tri.CubicTriInterpolator(self._triv, z) return F(x, y) elif kind == 'barycentric': self.build_tri_voronoi() xyin = np.vstack([self.xv, self.yv]).T xyout = np.vstack([x, y]).T F = BarycentricInterp(xyin, xyout) return F(z) elif kind == 'nearest': if isinstance(x, float): dist, idx = self.find_nearest([x, y]) return z[idx] elif isinstance(x, np.ndarray): sz = x.shape xy = np.array([x.ravel(), y.ravel()]).T dist, idx = self.find_nearest(xy) return z[idx].reshape(sz)
def test_tri_smooth_gradient(): # Image comparison based on example trigradient_demo. def dipole_potential(x, y): """ An electric dipole potential V """ r_sq = x**2 + y**2 theta = np.arctan2(y, x) z = np.cos(theta) / r_sq return (np.max(z) - z) / (np.max(z) - np.min(z)) # Creating a Triangulation n_angles = 30 n_radii = 10 min_radius = 0.2 radii = np.linspace(min_radius, 0.95, n_radii) angles = np.linspace(0, 2 * np.pi, n_angles, endpoint=False) angles = np.repeat(angles[..., np.newaxis], n_radii, axis=1) angles[:, 1::2] += np.pi / n_angles x = (radii * np.cos(angles)).flatten() y = (radii * np.sin(angles)).flatten() V = dipole_potential(x, y) triang = mtri.Triangulation(x, y) xmid = x[triang.triangles].mean(axis=1) ymid = y[triang.triangles].mean(axis=1) mask = np.where(xmid * xmid + ymid * ymid < min_radius * min_radius, 1, 0) triang.set_mask(mask) # Refine data - interpolates the electrical potential V refiner = mtri.UniformTriRefiner(triang) tri_refi, z_test_refi = refiner.refine_field(V, subdiv=3) # Computes the electrical field (Ex, Ey) as gradient of -V tci = mtri.CubicTriInterpolator(triang, -V) (Ex, Ey) = tci.gradient(triang.x, triang.y) E_norm = np.sqrt(Ex**2 + Ey**2) # Plot the triangulation, the potential iso-contours and the vector field plt.figure() plt.gca().set_aspect('equal') plt.triplot(triang, color='0.8') levels = np.arange(0., 1., 0.01) cmap = cm.get_cmap(name='hot', lut=None) plt.tricontour(tri_refi, z_test_refi, levels=levels, cmap=cmap, linewidths=[2.0, 1.0, 1.0, 1.0]) # Plots direction of the electrical vector field plt.quiver(triang.x, triang.y, Ex / E_norm, Ey / E_norm, units='xy', scale=10., zorder=3, color='blue', width=0.007, headwidth=3., headlength=4.)
def resample(df, n=50): t = tri.Triangulation(df.X, df.Y) def rng(t): return np.linspace(t.min(), t.max(), n) xi, yi = np.meshgrid(rng(df.X), rng(df.Y)) interp = tri.CubicTriInterpolator(t, df.Z) zi = interp(xi, yi) dfi = pd.DataFrame(dict(Z=zi.flatten()), index=pd.MultiIndex.from_tuples(zip( xi.flatten(), yi.flatten()), names=["X", "Y"])) return dfi
def addInterpolator(self, interpolation='cubic', kind='geom'): ''' Add interpolator Object. ''' self.interType = interpolation self.interKind = kind if self.interType == 'cubic': self.s_i = tri.CubicTriInterpolator(self.triangulation, self.s, kind=self.interKind) elif self.interType == 'linear': self.s_i = tri.LinearTriInterpolator(self.triangulation, self.s) else: raise ValueError('Interpolation must be "cubic" or "linear".')
def interpolate_volume_fraction(self, xi, yi): """Interpolate volume fraction at given points. Parameters ---------- xi, yi - array-like : x and y coordinates of interpolation points Returns ------- f - array-like : interpolated volume fraction """ self.interpolator_f = tri.CubicTriInterpolator( self.triang, self.data['f'].values, kind='geom') return self.interpolator_f(xi, yi)
def addInterpolator(self, interpolation='cubic', kind='geom'): ''' Add interpolator Object to the vector field. ''' self.interType = interpolation self.interKind = kind if self.interType == 'cubic': self.txx_i = tri.CubicTriInterpolator(self.triangulation, self.txx, kind=self.interKind) self.txy_i = tri.CubicTriInterpolator(self.triangulation, self.txy, kind=self.interKind) self.txz_i = tri.CubicTriInterpolator(self.triangulation, self.txz, kind=self.interKind) self.tyy_i = tri.CubicTriInterpolator(self.triangulation, self.tyy, kind=self.interKind) self.tyz_i = tri.CubicTriInterpolator(self.triangulation, self.tyz, kind=self.interKind) self.tzz_i = tri.CubicTriInterpolator(self.triangulation, self.tzz, kind=self.interKind) elif self.interType == 'linear': self.txx_i = tri.LinearTriInterpolator(self.triangulation, self.txx) self.txy_i = tri.LinearTriInterpolator(self.triangulation, self.txy) self.txz_i = tri.LinearTriInterpolator(self.triangulation, self.txz) self.tyy_i = tri.LinearTriInterpolator(self.triangulation, self.tyy) self.tyz_i = tri.LinearTriInterpolator(self.triangulation, self.tyz) self.tzz_i = tri.LinearTriInterpolator(self.triangulation, self.tzz) else: raise ValueError('Interpolation must be "cubic" or "linear".') # # # def addGradient(self): # ''' # Calculate and save the gradient at all point of the grid. # ''' # dsdx, dsdy = self.gradientxy(self.x,self.y) # self.data['dsdx'] = dsdx # self.data['dsdy'] = dsdy
def make_heat_map(x, y, values): values = np.array(values) min_x, min_y, max_x, max_y = min(x), min(y), max(x), max(y) tick_count = round(len(values) ** 2) xticks = np.linspace(min_x, max_x, tick_count) yticks = np.linspace(min_y, max_y, tick_count) xv, yv = np.meshgrid(xticks, yticks) try: import scipy.interpolate # pylint: disable=import-outside-toplevel points = np.column_stack((x, y)) heat_map = scipy.interpolate.griddata(points, values, (xv, yv), method="cubic") except ImportError: import matplotlib.tri as tri # pylint: disable=import-outside-toplevel triang = tri.Triangulation(x, y) interpolator = tri.CubicTriInterpolator(triang, values) heat_map = interpolator(xv, yv) return heat_map, xv, yv, min_x, min_y, max_x, max_y
def solve(self, params): ''' Performs a forward solve with the given parameters and returns a 2D matrix representing the temperature distribution of a thermal fin with values interpolated from a finite element grid Arguments: params: Array of conductivities [k1, k2, k3, k4, Biot, k5] Returns theta : Temperature distribution on a grid, x ∈ [-3, 3] and y ∈ [0, 4] ''' Ah = coo_matrix((self.nodes, self.nodes)) for param, Aq in zip(params, self.Aq_s): Ah = Ah + param * Aq uh = spsolve(Ah, self.Fh) interpolator = tri.CubicTriInterpolator(self.triangulation, uh) uh_interpolated = interpolator(self.xx, self.yy) return np.ma.fix_invalid(uh_interpolated, fill_value = 0.0).data
def test_triinterpcubic_geom_weights(): # Tests to check computation of weights for _DOF_estimator_geom: # The weight sum per triangle can be 1. (in case all angles < 90 degrees) # or (2*w_i) where w_i = 1-alpha_i/np.pi is the weight of apex i ; alpha_i # is the apex angle > 90 degrees. (ax, ay) = (0., 1.687) x = np.array([ax, 0.5 * ax, 0., 1.]) y = np.array([ay, -ay, 0., 0.]) z = np.zeros(4, dtype=np.float64) triangles = [[0, 2, 3], [1, 3, 2]] sum_w = np.zeros([4, 2]) # 4 possibilities ; 2 triangles for theta in np.linspace(0., 2 * np.pi, 14): # rotating the figure... x_rot = np.cos(theta) * x + np.sin(theta) * y y_rot = -np.sin(theta) * x + np.cos(theta) * y triang = mtri.Triangulation(x_rot, y_rot, triangles) cubic_geom = mtri.CubicTriInterpolator(triang, z, kind='geom') dof_estimator = mtri.triinterpolate._DOF_estimator_geom(cubic_geom) weights = dof_estimator.compute_geom_weights() # Testing for the 4 possibilities... sum_w[0, :] = np.sum(weights, 1) - 1 for itri in range(3): sum_w[itri + 1, :] = np.sum(weights, 1) - 2 * weights[:, itri] assert_array_almost_equal(np.min(np.abs(sum_w), axis=0), np.array([0., 0.], dtype=np.float64))
line = [] for x in x_grid: # if we do not have a value use NaN # also dance around doing a look up on keys that don't exist if x in heights: line.append(heights[x][y] if y in heights[x] else np.nan) else: line.append(np.nan) z_grid.append(line) # interpolate the data between our observation lines triang = tri.Triangulation(x_array, y_array) #interpolator = tri.LinearTriInterpolator(triang, z_array) interpolator = tri.CubicTriInterpolator(triang, z_array, kind='min_E', trifinder=None, dz=None) Xi, Yi = np.meshgrid(x_grid, y_grid) zi = interpolator(Xi, Yi) # calculate the fill needed using interpolated data # NOTE: this uses the bounds of the x and y grid # but the interpolation does not go the full bounds cubic_yards_interpolated = sum( [np.trapz([j for j in i if not np.isnan(j)]) for i in zi.data]) / 27 # with commas cu_yrds_fmt_interp = "{:,}".format(int(cubic_yards_interpolated.round())) # plot contour surface fig = plt.figure()
def test_triinterp_transformations(): # 1) Testing that the interpolation scheme is invariant by rotation of the # whole figure. # Note: This test is non-trivial for a CubicTriInterpolator with # kind='min_E'. It does fail for a non-isotropic stiffness matrix E of # :class:`_ReducedHCT_Element` (tested with E=np.diag([1., 1., 1.])), and # provides a good test for :meth:`get_Kff_and_Ff`of the same class. # # 2) Also testing that the interpolation scheme is invariant by expansion # of the whole figure along one axis. n_angles = 20 n_radii = 10 min_radius = 0.15 def z(x, y): r1 = np.sqrt((0.5 - x)**2 + (0.5 - y)**2) theta1 = np.arctan2(0.5 - x, 0.5 - y) r2 = np.sqrt((-x - 0.2)**2 + (-y - 0.2)**2) theta2 = np.arctan2(-x - 0.2, -y - 0.2) z = -(2 * (np.exp( (r1 / 10)**2) - 1) * 30. * np.cos(7. * theta1) + (np.exp( (r2 / 10)**2) - 1) * 30. * np.cos(11. * theta2) + 0.7 * (x**2 + y**2)) return (np.max(z) - z) / (np.max(z) - np.min(z)) # First create the x and y coordinates of the points. radii = np.linspace(min_radius, 0.95, n_radii) angles = np.linspace(0 + n_angles, 2 * np.pi + n_angles, n_angles, endpoint=False) angles = np.repeat(angles[..., np.newaxis], n_radii, axis=1) angles[:, 1::2] += np.pi / n_angles x0 = (radii * np.cos(angles)).flatten() y0 = (radii * np.sin(angles)).flatten() triang0 = mtri.Triangulation(x0, y0) # Delaunay triangulation z0 = z(x0, y0) # Then create the test points xs0 = np.linspace(-1., 1., 23) ys0 = np.linspace(-1., 1., 23) xs0, ys0 = np.meshgrid(xs0, ys0) xs0 = xs0.ravel() ys0 = ys0.ravel() interp_z0 = {} for i_angle in range(2): # Rotating everything theta = 2 * np.pi / n_angles * i_angle x = np.cos(theta) * x0 + np.sin(theta) * y0 y = -np.sin(theta) * x0 + np.cos(theta) * y0 xs = np.cos(theta) * xs0 + np.sin(theta) * ys0 ys = -np.sin(theta) * xs0 + np.cos(theta) * ys0 triang = mtri.Triangulation(x, y, triang0.triangles) linear_interp = mtri.LinearTriInterpolator(triang, z0) cubic_min_E = mtri.CubicTriInterpolator(triang, z0) cubic_geom = mtri.CubicTriInterpolator(triang, z0, kind='geom') dic_interp = { 'lin': linear_interp, 'min_E': cubic_min_E, 'geom': cubic_geom } # Testing that the interpolation is invariant by rotation... for interp_key in ['lin', 'min_E', 'geom']: interp = dic_interp[interp_key] if i_angle == 0: interp_z0[interp_key] = interp(xs0, ys0) # storage else: interpz = interp(xs, ys) matest.assert_array_almost_equal(interpz, interp_z0[interp_key]) scale_factor = 987654.3210 for scaled_axis in ('x', 'y'): # Scaling everything (expansion along scaled_axis) if scaled_axis == 'x': x = scale_factor * x0 y = y0 xs = scale_factor * xs0 ys = ys0 else: x = x0 y = scale_factor * y0 xs = xs0 ys = scale_factor * ys0 triang = mtri.Triangulation(x, y, triang0.triangles) linear_interp = mtri.LinearTriInterpolator(triang, z0) cubic_min_E = mtri.CubicTriInterpolator(triang, z0) cubic_geom = mtri.CubicTriInterpolator(triang, z0, kind='geom') dic_interp = { 'lin': linear_interp, 'min_E': cubic_min_E, 'geom': cubic_geom } # Testing that the interpolation is invariant by expansion along # 1 axis... for interp_key in ['lin', 'min_E', 'geom']: interpz = dic_interp[interp_key](xs, ys) matest.assert_array_almost_equal(interpz, interp_z0[interp_key])
def _calc_subaperture(self, interp: ndarray, x: int, y: int, method: str = 'cubic') -> ndarray: """Calculate a subaperture view from the raw sensor data. Args: interp : ndarray of :class:`scipy.interpolate.RectBivariateSpline` x: Distance from the microlens center in x-direction in pixels. y: Distance from the microlens center in y-direction in pixels. method: Used interpolation method. Available methods are: 'bilinear', 'cubic'. Default: 'cubic'. Returns: The calculated subaperture image. """ interp_param_list = ["cubic", "linear"] num_channels = interp.size if method not in interp_param_list: raise ValueError(f"Specified method '{method}' is not one of the " "recognized methods: {interp_param_list}") logger.debug( "Calculating subaperture with x = {} and y = {}...".format(x, y)) # Calculate interpolation coordinates by given distance x and y interp_coordinates = np.asarray(self._microlensCenters) interp_coordinates_x = interp_coordinates[:, 0] + x interp_coordinates_y = interp_coordinates[:, 1] + y # Do a Delaunay triangulation of the interpolation points logger.debug("Calculating Delaunay triangulation of " "subaperture interpolation points....") triang = mtri.Triangulation(interp_coordinates_x, interp_coordinates_y) logger.debug("...done.") # Get size of the original image from interp object x_max = int(interp[0].tck[0].max() + 1) y_max = int(interp[0].tck[1].max() + 1) # Size of subaperture image s_max = int(x_max / self._microlensSize) t_max = int(y_max / self._microlensSize) # Rectangular grid for final image xi, yi = np.meshgrid(np.linspace(0, x_max, s_max), np.linspace(0, y_max, t_max)) # Initialize final image subaperture_image = np.zeros((s_max, t_max, num_channels), dtype=np.float64) # Check if (x,y) coordinates are still inside microlens, # if not, return black image # if x**2 + y**2 > self._microlensRadius**2: # return subaperture_image # Iterate over image channels and fill final image for i in range(0, num_channels): logger.debug( "Interpolating subaperture image channel {}.".format(i)) # Do a cubic interpolation on the triangular grid if method == "cubic": interp_geom = mtri.CubicTriInterpolator( triang, interp[i].ev(interp_coordinates_x, interp_coordinates_y), kind='geom') # Alternatively, do a linear interpolation elif method == "linear": interp_geom = mtri.LinearTriInterpolator( triang, interp[i].ev(interp_coordinates_x, interp_coordinates_y)) subaperture_image[:, :, i] = np.flipud(np.rot90(interp_geom(xi, yi))) logger.debug("...done.") del interp_geom logger.debug("...done.") return np.squeeze(np.nan_to_num(subaperture_image))
def test_triinterp(): # Test points within triangles of masked triangulation. x, y = np.meshgrid(np.arange(4), np.arange(4)) x = x.ravel() y = y.ravel() z = 1.23 * x - 4.79 * y triangles = [[0, 1, 4], [1, 5, 4], [1, 2, 5], [2, 6, 5], [2, 3, 6], [3, 7, 6], [4, 5, 8], [5, 9, 8], [5, 6, 9], [6, 10, 9], [6, 7, 10], [7, 11, 10], [8, 9, 12], [9, 13, 12], [9, 10, 13], [10, 14, 13], [10, 11, 14], [11, 15, 14]] mask = np.zeros(len(triangles)) mask[8:10] = 1 triang = mtri.Triangulation(x, y, triangles, mask) linear_interp = mtri.LinearTriInterpolator(triang, z) cubic_min_E = mtri.CubicTriInterpolator(triang, z) cubic_geom = mtri.CubicTriInterpolator(triang, z, kind='geom') xs = np.linspace(0.25, 2.75, 6) ys = [0.25, 0.75, 2.25, 2.75] xs, ys = np.meshgrid(xs, ys) # Testing arrays with array.ndim = 2 for interp in (linear_interp, cubic_min_E, cubic_geom): zs = interp(xs, ys) assert_array_almost_equal(zs, (1.23 * xs - 4.79 * ys)) # Test points outside triangulation. xs = [-0.25, 1.25, 1.75, 3.25] ys = xs xs, ys = np.meshgrid(xs, ys) for interp in (linear_interp, cubic_min_E, cubic_geom): zs = linear_interp(xs, ys) assert_array_equal(zs.mask, [[True] * 4] * 4) # Test mixed configuration (outside / inside). xs = np.linspace(0.25, 1.75, 6) ys = [0.25, 0.75, 1.25, 1.75] xs, ys = np.meshgrid(xs, ys) for interp in (linear_interp, cubic_min_E, cubic_geom): zs = interp(xs, ys) matest.assert_array_almost_equal(zs, (1.23 * xs - 4.79 * ys)) mask = (xs >= 1) * (xs <= 2) * (ys >= 1) * (ys <= 2) assert_array_equal(zs.mask, mask) # 2nd order patch test: on a grid with an 'arbitrary shaped' triangle, # patch test shall be exact for quadratic functions and cubic # interpolator if *kind* = user (a, b, c) = (1.23, -4.79, 0.6) def quad(x, y): return a * (x - 0.5)**2 + b * (y - 0.5)**2 + c * x * y def gradient_quad(x, y): return (2 * a * (x - 0.5) + c * y, 2 * b * (y - 0.5) + c * x) x = np.array([0.2, 0.33367, 0.669, 0., 1., 1., 0.]) y = np.array([0.3, 0.80755, 0.4335, 0., 0., 1., 1.]) triangles = np.array([[0, 1, 2], [3, 0, 4], [4, 0, 2], [4, 2, 5], [1, 5, 2], [6, 5, 1], [6, 1, 0], [6, 0, 3]]) triang = mtri.Triangulation(x, y, triangles) z = quad(x, y) dz = gradient_quad(x, y) # test points for 2nd order patch test xs = np.linspace(0., 1., 5) ys = np.linspace(0., 1., 5) xs, ys = np.meshgrid(xs, ys) cubic_user = mtri.CubicTriInterpolator(triang, z, kind='user', dz=dz) interp_zs = cubic_user(xs, ys) assert_array_almost_equal(interp_zs, quad(xs, ys)) (interp_dzsdx, interp_dzsdy) = cubic_user.gradient(x, y) (dzsdx, dzsdy) = gradient_quad(x, y) assert_array_almost_equal(interp_dzsdx, dzsdx) assert_array_almost_equal(interp_dzsdy, dzsdy) # Cubic improvement: cubic interpolation shall perform better than linear # on a sufficiently dense mesh for a quadratic function. n = 11 x, y = np.meshgrid(np.linspace(0., 1., n + 1), np.linspace(0., 1., n + 1)) x = x.ravel() y = y.ravel() z = quad(x, y) triang = mtri.Triangulation(x, y, triangles=meshgrid_triangles(n + 1)) xs, ys = np.meshgrid(np.linspace(0.1, 0.9, 5), np.linspace(0.1, 0.9, 5)) xs = xs.ravel() ys = ys.ravel() linear_interp = mtri.LinearTriInterpolator(triang, z) cubic_min_E = mtri.CubicTriInterpolator(triang, z) cubic_geom = mtri.CubicTriInterpolator(triang, z, kind='geom') zs = quad(xs, ys) diff_lin = np.abs(linear_interp(xs, ys) - zs) for interp in (cubic_min_E, cubic_geom): diff_cubic = np.abs(interp(xs, ys) - zs) assert (np.max(diff_lin) >= 10. * np.max(diff_cubic)) assert (np.dot(diff_lin, diff_lin) >= 100. * np.dot(diff_cubic, diff_cubic))
def test_triinterpcubic_C1_continuity(): # Below the 4 tests which demonstrate C1 continuity of the # TriCubicInterpolator (testing the cubic shape functions on arbitrary # triangle): # # 1) Testing continuity of function & derivatives at corner for all 9 # shape functions. Testing also function values at same location. # 2) Testing C1 continuity along each edge (as gradient is polynomial of # 2nd order, it is sufficient to test at the middle). # 3) Testing C1 continuity at triangle barycenter (where the 3 subtriangles # meet) # 4) Testing C1 continuity at median 1/3 points (midside between 2 # subtriangles) # Utility test function check_continuity def check_continuity(interpolator, loc, values=None): """ Checks the continuity of interpolator (and its derivatives) near location loc. Can check the value at loc itself if *values* is provided. *interpolator* TriInterpolator *loc* location to test (x0, y0) *values* (optional) array [z0, dzx0, dzy0] to check the value at *loc* """ n_star = 24 # Number of continuity points in a boundary of loc epsilon = 1.e-10 # Distance for loc boundary k = 100. # Continuity coefficient (loc_x, loc_y) = loc star_x = loc_x + epsilon * np.cos(np.linspace(0., 2 * np.pi, n_star)) star_y = loc_y + epsilon * np.sin(np.linspace(0., 2 * np.pi, n_star)) z = interpolator([loc_x], [loc_y])[0] (dzx, dzy) = interpolator.gradient([loc_x], [loc_y]) if values is not None: assert_array_almost_equal(z, values[0]) assert_array_almost_equal(dzx[0], values[1]) assert_array_almost_equal(dzy[0], values[2]) diff_z = interpolator(star_x, star_y) - z (tab_dzx, tab_dzy) = interpolator.gradient(star_x, star_y) diff_dzx = tab_dzx - dzx diff_dzy = tab_dzy - dzy assert_array_less(diff_z, epsilon * k) assert_array_less(diff_dzx, epsilon * k) assert_array_less(diff_dzy, epsilon * k) # Drawing arbitrary triangle (a, b, c) inside a unit square. (ax, ay) = (0.2, 0.3) (bx, by) = (0.33367, 0.80755) (cx, cy) = (0.669, 0.4335) x = np.array([ax, bx, cx, 0., 1., 1., 0.]) y = np.array([ay, by, cy, 0., 0., 1., 1.]) triangles = np.array([[0, 1, 2], [3, 0, 4], [4, 0, 2], [4, 2, 5], [1, 5, 2], [6, 5, 1], [6, 1, 0], [6, 0, 3]]) triang = mtri.Triangulation(x, y, triangles) for idof in range(9): z = np.zeros(7, dtype=np.float64) dzx = np.zeros(7, dtype=np.float64) dzy = np.zeros(7, dtype=np.float64) values = np.zeros([3, 3], dtype=np.float64) case = idof // 3 values[case, idof % 3] = 1.0 if case == 0: z[idof] = 1.0 elif case == 1: dzx[idof % 3] = 1.0 elif case == 2: dzy[idof % 3] = 1.0 interp = mtri.CubicTriInterpolator(triang, z, kind='user', dz=(dzx, dzy)) # Test 1) Checking values and continuity at nodes check_continuity(interp, (ax, ay), values[:, 0]) check_continuity(interp, (bx, by), values[:, 1]) check_continuity(interp, (cx, cy), values[:, 2]) # Test 2) Checking continuity at midside nodes check_continuity(interp, ((ax + bx) * 0.5, (ay + by) * 0.5)) check_continuity(interp, ((ax + cx) * 0.5, (ay + cy) * 0.5)) check_continuity(interp, ((cx + bx) * 0.5, (cy + by) * 0.5)) # Test 3) Checking continuity at barycenter check_continuity(interp, ((ax + bx + cx) / 3., (ay + by + cy) / 3.)) # Test 4) Checking continuity at median 1/3-point check_continuity(interp, ((4. * ax + bx + cx) / 6., (4. * ay + by + cy) / 6.)) check_continuity(interp, ((ax + 4. * bx + cx) / 6., (ay + 4. * by + cy) / 6.)) check_continuity(interp, ((ax + bx + 4. * cx) / 6., (ay + by + 4. * cy) / 6.))
def plot_topomap(conditions, time, vrange=None, fig_title='placeholder_title', show_sensors=False, show_head=True, nlevels=10, contour=True): r, c = dimensions(conditions) fig, axes = plt.subplots(r, c, figsize=(5 * c, 5 * r)) if isinstance(conditions, str): conditions = [conditions] z = {} #1D information Z = {} #interpolated data #parse time input and create appropriate z variables if isinstance(time, list): if len(time) == 2: if in_range(time, t): print(time) lower, upper = time[0], time[1] if lower < upper: if r > 1: for row in conditions: for condition in row: z[condition] = dfs[condition][ (dfs[condition]['t'] > lower) & (dfs[condition]['t'] < upper )].loc[:, 'Fp1':'O2'].mean() else: for condition in conditions: z[condition] = dfs[condition][ (dfs[condition]['t'] > lower) & (dfs[condition]['t'] < upper )].loc[:, 'Fp1':'O2'].mean() else: raise ValueError( 'Ensure that the range you provide is defined as [lower,upper]' ) else: raise ValueError( 'Provided array contains elements outside of time range') else: raise ValueError( 'Provided time range: %s, should only have 2 elements' % time) elif isinstance(time, float) or isinstance(time, int): if in_range(time, t): if time not in t: time_adj = time - ((time + 200) % 1.953125) print("Provided time: %s, was adjusted to: %s." % (time, time_adj)) time = time_adj if r > 1: for row in conditions: for condition in row: z[condition] = dfs[condition][( dfs[condition]['t'] == time )].loc[:, 'Fp1':'O2'].mean() else: for condition in conditions: z[condition] = dfs[condition][( dfs[condition]['t'] == time)].loc[:, 'Fp1':'O2'].mean() else: raise ValueError('Provided time: %s, is out of range' % time) else: raise TypeError( 'Provided time: %s of %s type, is invalid. Enter a range or a single time point' % (time, type(time))) #set vmax and vmin from provided parameters or data if isinstance(vrange, list): if len(vrange) == 2: vmin, vmax = vrange[0], vrange[1] if vmin > vmax: raise ValueError( 'Ensure that vrange is provided in form [min,max].') else: raise ValueError( 'Provided vrange has %s elements. Should only have 2.' % (len(vrange))) elif vrange == None: vmin, vmax = np.inf, np.NINF for condition, data in z.items(): temp_vmin, temp_vmax = data.min(), data.max() if temp_vmax > vmax: vmax = temp_vmax if temp_vmin < vmin: vmin = temp_vmin vmin *= 1.1 vmax *= 1.1 else: raise TypeError( 'Provided vrange: %s of %s type is invalid. Enter a range [min,max] or None.' % (vrange, type(vrange))) print('The range is %s to %s.' % (vmin, vmax)) triangles = tri.Triangulation(x, y) for condition in z: tri_interp = tri.CubicTriInterpolator(triangles, z[condition]) Z[condition] = tri_interp(X, Y) def _plot_topomap(ax, contour, Z): global cm if contour: cm = ax.contourf(X, Y, Z, np.arange(vmin, vmax + .1, (vmax - vmin) / nlevels), cmap=plt.cm.jet, vmax=vmax, vmin=vmin) else: cm = ax.pcolor(X, Y, Z, cmap=plt.cm.jet, vmax=vmax, vmin=vmin) #formatting changes to set the plot size and remove axes ax.axis('off') ax.set_ylim([-1.2, 1.2]) ax.set_xlim([-1.2, 1.2]) #mask electrodes that don't fit in the circle i.e. PO3 PO4 and Iz mask = patches.Wedge((0, 0), 1.6, 0, 360, width=0.6, color='white') ax.add_artist(mask) if show_sensors: ax.plot(x, y, color="#444444", marker="o", linestyle="", markersize=2) if show_head: #draw head_border = plt.Circle((0, 0), 1, color='black', fill=False) LNose = lines.Line2D([-0.087, 0], [0.996, 1.1], color='black', solid_capstyle='round', lw=1) RNose = lines.Line2D([0.087, 0], [0.996, 1.1], color='black', solid_capstyle='round', lw=1) LEar = patches.Wedge((-1, 0), 0.1, 90, 270, width=0.0025, color='black') REar = patches.Wedge((1, 0), 0.1, 270, 90, width=0.0025, color='black') #add ax.add_artist(head_border) ax.add_line(LNose) ax.add_line(RNose) ax.add_artist(LEar) ax.add_artist(REar) i = 0 if r > 1: #grid or col for row in axes: if c > 1: #grid j = 0 for ax in row: _plot_topomap(ax, contour, Z[conditions[i][j]]) j += 1 else: #col _plot_topomap(row, contour, Z[conditions[i]]) i += 1 elif c > 1: #row for ax in axes: _plot_topomap(ax, contour, Z[conditions[i]]) i += 1 else: #single plot _plot_topomap(axes, contour, Z[conditions[0]]) #adjust plot and add color bar fig.subplots_adjust(right=0.8, top=0.85, bottom=0.15) cbar_ax = fig.add_axes([0.85, 0.15, 0.025, 0.7]) fig.colorbar(cm, cax=cbar_ax) #save file path = directory_in_str + os.sep + 'Plots' + os.sep fig.savefig(path + fig_title + '.pdf', format='pdf') print('Plotted successfully! Navigate to %s to find %s.pdf' % (path, fig_title))
# Create triangulation. x = np.asarray([0, 1, 2, 3, 0.5, 1.5, 2.5, 1, 2, 1.5]) y = np.asarray([0, 0, 0, 0, 1.0, 1.0, 1.0, 2, 2, 3.0]) triangles = [[0, 1, 4], [1, 2, 5], [2, 3, 6], [1, 5, 4], [2, 6, 5], [4, 5, 7], [5, 6, 8], [5, 8, 7], [7, 8, 9]] triang = mtri.Triangulation(x, y, triangles) # Interpolate to regularly-spaced quad grid. z = np.cos(1.5 * x) * np.cos(1.5 * y) xi, yi = np.meshgrid(np.linspace(0, 3, 20), np.linspace(0, 3, 20)) interp_lin = mtri.LinearTriInterpolator(triang, z) zi_lin = interp_lin(xi, yi) interp_cubic_geom = mtri.CubicTriInterpolator(triang, z, kind='geom') zi_cubic_geom = interp_cubic_geom(xi, yi) interp_cubic_min_E = mtri.CubicTriInterpolator(triang, z, kind='min_E') zi_cubic_min_E = interp_cubic_min_E(xi, yi) # Set up the figure fig, axs = plt.subplots(nrows=2, ncols=2) axs = axs.flatten() # Plot the triangulation. axs[0].tricontourf(triang, z) axs[0].triplot(triang, 'ko-') axs[0].set_title('Triangular grid') # Plot linear interpolation to quad grid.
def plot_contour_map(file_name, stress_name, level, color, title, fsize, contour_level=10): ''' file_name: name of dataframe to use stress_name: name of stresses or forces to by analyzed level = level or range of stresses and its interval. List. color = color or contour map for cmap. e.g. plt.cm.Spectral. title = title of chart. String. fzise = figure size. List ''' # import statements import numpy as np import seaborn as sns import matplotlib.pyplot as plt import matplotlib.tri as tri import pandas as pd import matplotlib.lines as lines # reading data from excel and converting it to pandas dataframe df = pd.read_excel(file_name, index_col='Joint') sns.set(style="white") # mesh values x = df['GlobalX (mm)']/1000 y = df['GlobalY (mm)']/1000 z = df[stress_name] # making figure to plot on fig = plt.figure(figsize=fsize) ax = fig.add_subplot(111) # plotting columns plt.plot(8, 26.9, marker='o', markersize=10, color="white", zorder = 15, label ='C6', alpha = 0.5) plt.plot(16, 26.9, marker='o', markersize=10, color="white", zorder = 15, label ='C7', alpha = 0.5) plt.plot(4.1, 22.75, marker='o', markersize=10, color="white", zorder = 15, label ='C11', alpha = 0.5) plt.plot(4.1, 18.9, marker='o', markersize=10, color="white", zorder = 15, label ='C13', alpha = 0.5) plt.plot(8, 18.9, marker='o', markersize=10, color="white", zorder = 15, label ='C14', alpha = 0.5) plt.plot(16, 18.9, marker='o', markersize=10, color="white", zorder = 15, label ='C15', alpha = 0.5) plt.plot(16, 10.9, marker='o', markersize=10, color="white", zorder = 15, label ='C19', alpha = 0.5) plt.plot(8, 2.9, marker='o', markersize=10, color="white", zorder = 15, label ='C24', alpha = 0.5) plt.plot(16, 2.9, marker='o', markersize=10, color="white", zorder = 15, label ='C25', alpha = 0.5) # annotating columns n = ['C6','C7', 'C11', 'C13', 'C14', 'C15', 'C19', 'C24', 'C25'] a = [8,16,4.1,4.1,8,16,16,8,16] b = [26.9,26.9,22.75,18.9,18.9,18.9,10.9,2.9,2.9] for i, txt in enumerate(n): ax.annotate(txt, (a[i]+0.2, b[i]+0.2), color = 'white') # plotting Shearwall SW-1 as lines line1 = lines.Line2D([4.552,4.552],[13.24,16.19], linewidth=7, color='white', alpha = 0.5) line2 = lines.Line2D([4.552,9.852],[16.19,16.19], linewidth=7, color='white', alpha = 0.5) line3 = lines.Line2D([9.852,9.852],[13.24,16.90], linewidth=7, color='white', alpha = 0.5) line4 = lines.Line2D([12.502,12.502],[13.24,16.90], linewidth=7, color='white', alpha = 0.5) line5 = lines.Line2D([9.852,12.502],[16.90,16.90], linewidth=7, color='white', alpha = 0.5) ax.add_line(line1) ax.add_line(line2) ax.add_line(line3) ax.add_line(line4) ax.add_line(line5) ax.annotate('SW-1', (6.5,14.54), color = 'white') # plotting Shearwall SW-2 as lines line6 = lines.Line2D([4.552,4.552],[6.11,9.06], linewidth=7, color='white', alpha = 0.5) line7 = lines.Line2D([12.502,12.502],[6.11,9.06], linewidth=7, color='white', alpha = 0.5) line8 = lines.Line2D([4.552,12.502],[6.11,6.11], linewidth=7, color='white', alpha = 0.5) ax.add_line(line6) ax.add_line(line7) ax.add_line(line8) ax.annotate('SW-2', (7.8,7.5), color = 'white') # making plot mesh and interpolation of x,y and z values for contour map nptsx, nptsy = len(x), len(y) xg, yg = np.meshgrid(np.linspace(x.min(), x.max(), nptsx), np.linspace(y.min(), y.max(), nptsy)) triangles = tri.Triangulation(x, y) tri_interp = tri.CubicTriInterpolator(triangles, z) zg = tri_interp(xg, yg) # change levels here according to your data levels = np.linspace(level[0], level[1], level[2]) colormap = ax.contourf(xg, yg, zg, levels, cmap=color, norm=plt.Normalize(vmax=z.max(), vmin=z.min()), zorder = 0) # add a colorbar fig.colorbar(colormap, orientation='vertical', # horizontal colour bar shrink=1.0, ticks=np.linspace(level[0], level[1], level[2])) # adding contour lines contours = plt.contour(xg, yg, zg, contour_level, colors='black') plt.clabel(contours, inline = True, fontsize = 10, fmt='%1.0f') # making gridlines plt.xticks(np.linspace(x.min(),x.max(),15)) plt.yticks(np.linspace(y.min(),y.max(),20)) ax.xaxis.grid(True, zorder=10, linestyle = '--', color = 'white', alpha = 0.2) ax.yaxis.grid(True, zorder=10, linestyle = '--', color = 'white', alpha = 0.2) ax.set_aspect("equal", "box") # plot title and label plt.title(title) plt.xlabel('X (m)') plt.ylabel('Y (m)') # show plot plt.show()
fig = plt.figure() ax0 = fig.add_subplot(111, projection='3d') # 生成结构化网格数据 coords = data x = coords['X'] y = coords['Y'] z = np.array(coords['Z']) triang = mtri.Triangulation(x, y) # Interpolate to regularly-spaced quad grid. xi, yi = np.meshgrid(np.linspace(min(x), max(x), 100), np.linspace(min(y), max(y), 100)) # interp_z = mtri.LinearTriInterpolator(triang, z) interp_z = mtri.CubicTriInterpolator(triang, z,kind='geom') zi = interp_z(xi, yi) filename = path+'write_tec_pointOnly.dat' with open(filename, 'w') as f: # 如果filename不存在会自动创建, 'w'表示写数据,写之前会清空文件中的原有数据! f.write("TITLE\t=\t\"terrain\"\n") f.write("VARIABLES\t= \"X\",\"Y\",\"Z\"\n") f.write("ZONE\tT=\"P1\",\tN=") f.write(str(count)) f.write(",\tE=\t") f.write(str(len(triang.triangles))) f.write(",DATAPACKING=POINT, ZONETYPE=FETRIANGLE\n") for i in range(count): f.write(str(x[i])+"\t") f.write(str(y[i])+"\t") f.write(str(z[i]))
def density_contour(hexbin, ax=None, c='k', colors='grey', alpha=1, clabels=True): """ Create a density contour plot. Parameters ---------- xdata : numpy.ndarray ydata : numpy.ndarray nbins_x : int Number of bins along x dimension nbins_y : int Number of bins along y dimension ax : matplotlib.Axes (optional) If supplied, plot the contour to this axis. Otherwise, open a new figure contour_kwargs : dict kwargs to be passed to pyplot.contour() """ #H, xedges, yedges = np.histogram2d(xdata, ydata, bins=(nbins_x,nbins_y), normed=True) #x_bin_sizes = (xedges[1:] - xedges[:-1]).reshape((1,nbins_x)) #y_bin_sizes = (yedges[1:] - yedges[:-1]).reshape((nbins_y,1)) #pdf = (H*(x_bin_sizes[0,0]*y_bin_sizes[0,0])) #X, Y = 0.5*(xedges[1:]+xedges[:-1]), 0.5*(yedges[1:]+yedges[:-1]) pdf = hexbin.get_array() / np.sum(hexbin.get_array().flatten()) verts = hexbin.get_offsets() x = [verts[offc][0] for offc in xrange(verts.shape[0])] y = [verts[offc][1] for offc in xrange(verts.shape[0])] # Create the Triangulation; no triangles so Delaunay triangulation created. triang = tri.Triangulation(x, y) # Predict iso-pdf confidence levels one_sigma = so.brentq(find_confidence_interval, 0., 1., args=(pdf, 0.68), xtol=1e-20) two_sigma = so.brentq(find_confidence_interval, 0., 1., args=(pdf, 0.95), xtol=1e-20) three_sigma = so.brentq(find_confidence_interval, 0., 1., args=(pdf, 0.997), xtol=1e-20) #extreme = so.brentq(find_confidence_interval, 0., 1., args=(pdf, 0.9999)) levels = [one_sigma, two_sigma, three_sigma] #, extreme] # masking badly shaped triangles at the border of the triangular mesh. #min_circle_ratio = .01 #mask = tri.TriAnalyzer(triang).get_flat_tri_mask(min_circle_ratio) #triang.set_mask(mask) # Refine data #refiner = tri.UniformTriRefiner(triang) #triang, pdf = refiner.refine_field(pdf, subdiv=3) # define grid. X = np.sort(np.unique(x)) dX = X[1] - X[0] X = np.linspace(np.min(X) - dX, np.max(X) + dX, 1000) Y = np.sort(np.unique(y)) dY = Y[1] - Y[0] Y = np.linspace(np.min(Y) - dY, np.max(Y) + dY, 1000) # grid the data. #Z = griddata(x, y, pdf, X, Y, interp='linear')#'nn')# # Interpolate to regularly-spaced quad grid. X, Y = np.meshgrid(X, Y) interp_tri = tri.CubicTriInterpolator(triang, pdf, kind='geom') Z = interp_tri(X, Y) fmt = {} strs = ['68%', '95%', '99.7%', '99.99%'] # Label every other level using strings for l, s in zip(levels, strs): fmt[l] = s if ax == None: CS = plt.contour(X, Y, Z, levels=levels, origin="lower", linewidths=1., colors=colors, alpha=alpha) #CS = plt.tricontour(triang, pdf, levels=levels, origin="lower",linewidths=1., colors=colors, alpha=alpha) if clabels: labels = plt.clabel(CS, CS.levels, inline=False, fmt=fmt, fontsize=6, colors=c, alpha=1.) for l in labels: l.set_rotation(0) else: CS = ax.contour(X, Y, Z, levels=levels, origin="lower", linewidths=1., colors=colors, alpha=alpha) #CS = ax.tricontour(triang, pdf, levels=levels, origin="lower",linewidths=1., colors=colors, alpha=alpha) if clabels: labels = ax.clabel(CS, CS.levels, inline=False, fmt=fmt, fontsize=6, colors=c, alpha=1.) for l in labels: l.set_rotation(0) return ax
def mask_extrap(x,y,v,inplace=False,norm_xy=False,mpl_tri=True): ''' Extrapolate numpy array at masked points. Based on delaunay triangulation provided by matplotlib. ''' if np.ma.isMA(v) and v.size!=v.count(): mask=v.mask else: return v sh=v.shape x=x.ravel() y=y.ravel() v=v.ravel() mask=mask.ravel() if inplace: u=v else: u=v.copy() if norm_xy: rxy=(x.max()-x.min())/(y.max()-y.min()) y=y*rxy if not mpl_tri: from matplotlib import delaunay # deprecated in version 1.4 # nn_extrapolator may have problems dealing with regular grids, # nans may be obtained. One simple solution is to rotate the domain! x,y=rot2d(x,y,np.pi/3.) if 0: tri=delaunay.Triangulation(x[~mask],y[~mask]) u[mask]=tri.nn_extrapolator(u[~mask])(x[mask],y[mask]) else: # deal with repeated pairs (problem for nn_extrapolator) xy=x[~mask]+1j*y[~mask] xy,ii=np.unique(xy,1) tri=delaunay.Triangulation(x[~mask][ii],y[~mask][ii]) u[mask]=tri.nn_extrapolator(u[~mask][ii])(x[mask],y[mask]) if np.any(np.isnan(u)): mask=np.isnan(u) tri=delaunay.Triangulation(x[~mask],y[~mask]) u[mask]=tri.nn_extrapolator(u[~mask])(x[mask],y[mask]) else: import matplotlib.tri as mtri # add corners: xv=np.asarray([x.min()-1,x.max()+1,x.max()+1,x.min()-1]) yv=np.asarray([y.min()-1,y.min()-1,y.max()+1,y.max()+1]) vv=np.zeros(4,v.dtype) mv=np.zeros(4,'bool') for i in range(4): d=(x[~mask]-xv[i])**2+(y[~mask]-yv[i])**2 j=np.where(d==d.min())[0][0] vv[i]=u[~mask][j] #x=np.ma.hstack((x.flat,xv)) # use ravel at top instead! x=np.ma.hstack((x,xv)) y=np.ma.hstack((y,yv)) u=np.ma.hstack((u,vv)) mask=np.hstack((mask,mv)) tri=mtri.Triangulation(x[~mask],y[~mask]) print u.shape,x.shape,y.shape,mask.shape u[mask] = mtri.CubicTriInterpolator(tri, u[~mask])(x[mask],y[mask]) if np.any(np.isnan(u)): mask=np.isnan(u) tri=mtri.Triangulation(x[~mask],y[~mask]) u[mask]=mtri.CubicTriInterpolator(tri,u[~mask])(x[mask],y[mask]) u=u[:-4] u.shape=sh if not inplace: return u
def _griddata(x,y,v,xi,yi,extrap=True,tri=False,mask=False,**kargs): ''' Use griddata instead ''' mpl_tri=kargs.get('mpl_tri',True) tri_type=kargs.get('tri_type','cubic') # cubic or linear tri_kind=kargs.get('tri_kind','geom') # min_E or geom (for type cubic only) # warning, if x.shape=n,1 x[~mask] will also have 2 dims!! Thus better just use ravel... if x.shape!=x.size or y.shape!=y.size or v.shape!=v.size: x=x.ravel() y=y.ravel() v=v.ravel() if not mask is False: mask=mask.ravel() if mask is False: if np.ma.isMA(v) and np.ma.count_masked(v)>0: mask=v.mask else: mask=np.zeros(v.shape,'bool') if not mpl_tri: from matplotlib import delaunay # deprecated in version 1.4 if 0: if not tri: tri=delaunay.Triangulation(x[~mask],y[~mask]) if extrap: u=tri.nn_extrapolator(v[~mask])(xi,yi) else: u=tri.nn_interpolator(v[~mask])(xi,yi) else: # deal with repeated pairs (problem for nn_extrapolator) xy=x[~mask]+1j*y[~mask] xy,ii=np.unique(xy,1) if not tri: tri=delaunay.Triangulation(x[~mask][ii],y[~mask][ii]) if extrap: u=tri.nn_extrapolator(v[~mask][ii].data)(xi,yi) else: u=tri.nn_interpolator(v[~mask][ii])(xi,yi) else: import matplotlib.tri as mtri if extrap: # add corners: if 0: dx=(xi.max()-xi.min())/(1.*xi.size) dy=(yi.max()-yi.min())/(1.*yi.size) else: # higher distance from domain: dx=(xi.max()-xi.min()) dy=(yi.max()-yi.min()) xv=np.asarray([xi.min()-dx,xi.max()+dy,xi.max()+dx,xi.min()-dx]) yv=np.asarray([yi.min()-dy,yi.min()-dy,yi.max()+dy,yi.max()+dy]) vv=np.zeros(4,v.dtype) mv=np.zeros(4,'bool') for i in range(4): d=(x[~mask]-xv[i])**2+(y[~mask]-yv[i])**2 j=np.where(d==d.min())[0][0] vv[i]=v[~mask][j] x=np.ma.hstack((x,xv)) y=np.ma.hstack((y,yv)) v=np.ma.hstack((v,vv)) mask=np.hstack((mask,mv)) if not tri: tri=mtri.Triangulation(x[~mask],y[~mask]) if tri_type=='cubic': u = mtri.CubicTriInterpolator(tri, v[~mask],kind=tri_kind)(xi,yi) elif tri_type=='linear': u = mtri.LinearTriInterpolator(tri, v[~mask])(xi,yi) return u, tri