Python griddata meshgrid - python

in Python I want to interpolate some data using scipy.interpolate.griddata(x,y,z,xi,yi).
Since I want my unequal spaced original data on the X-Y grid map on an equal spaced XI-YI grid I have to use a meshgrid as:
X, Y = numpy.meshgrid([1,2,3], [2,5,6,8])
XI,YI = numpy.meshgrid([1,2,3],[4,5,6,7])
print scipy.interpolate.griddata(X,Y,X**2+Y**2,XI,YI)
Unfortunately it seems as scipys' griddata does not accept matrices as input for x,y,z in contrast to matlab's griddata-function. Does anyone has a hint for me how to solve the problem?

The correct call sequence in your case is
print scipy.interpolate.griddata((X.ravel(),Y.ravel()), (X**2+Y**2).ravel(), (XI, YI))
I.e., you need to cast the input data points to 1-d. (This could be fixed to work without the .ravel()s in the next version of Scipy.)

I think you need to reshape your grids, griddata expects a list of points with coordinates in column form:
points = transpose(reshape((X,Y), (2,12)))
pointsI = transpose(reshape((XI,YI), (2,12)))
Z = reshape(X**2+Y**2, 12)
print scipy.interpolate.griddata(points, Z, pointsI)

Related

interpolate / downsample 2D array in Python

I have 2 separate arrays with different sizes:
len(range_data) = 4320
len(az1) = 385
len(az2) = 347
data1.shape = (385,4320)
data2.shape = (347,4320)
I would like for the dimensions of data2 to equal that of data1, such that data2.shape should be (385,4320). I have tried scipy interpolate such as:
f = interpolate.interp2d(az1,range_data,data1,kind='cubic')
znew = f(az2,range_data)
print(znew.shape)
(347,4320)
znew.shape should be (385,4320), any ideas why this is happening and/or what might need to be done to fix this?
I don't think that interp2d actually generates more points for you, it defines an interpolation function over a grid. That means that what you've created is a way to interpolate points within the grid defined by your first set of data points. znew will return an interpolated grid with the same number of values as the x and y passed to it.
See the source code.
Returns
-------
z : 2-D array with shape (len(y), len(x))
The interpolated values.
If you want to add extra data points, I would suggest deriving a regression function (or whatever ML technique you want, NNs if you're so inclined) on the second data set and use that function to produce the extra 38 datapoints you need.

How to plot an array as if the indices i,j were the x,y coordinates?

Hi guys first question here, looked for an answer but could not find anything, I will try to give it my best.
I am currently working on a problem in the field of Computational Physics and I am solving the Navier-Stokes equations numerically using the Finite Difference Method. It`s my first time working with Python (using a Google Colaboratory notebook with Python 3). I am solving the equations for a grid of points in a two-dimensional plane. I created this grid using np.arrays
import numpy as np
import matplotlib.pyplot as plt
N = 10
data = np.zeros((N,N))
and then manipulating it. For example
for i in range(N):
for j in range(N):
data[i,j] = i
which makes the values of the array increase with index i. However, if I plot my data-array now using
x = np.arange(N)
y = np.arange(N)
plt.contourf(x, y, data)
plt.colorbar()
The result of the example:
It shows that the plotted data increases along the y-axis even though my manipulation of the array should make it increase along the x-axis.
I noticed this happens because the indexing of arrays (i,j) is different from the standard orientation of x- and y-axis, but how can I plot my data-array as if i=x and j=y?
You can use numpy's ndindex function to get the indices based on shape and then unzip the result.
x,y=list(zip(*np.ndindex((N,N))))
The data is row by column and can be obtained with meshgrid. If you're interested in the same manipulation. You can make the data with meshgrid as
dx,dy=np.meshgrid(np.arange(N),np.arange(N))
And then plot the dy to get variation in the x axis.

What does the Mayavi contour3d docs mean when it refers to "the arrows"?

I understand how to plot contours for a grid of data in mayavi like this:
from mayavi import mlab
mlab.contour3d(my_data_grid)
However, I'm curious what this other signature for the function is:
mlab.contour3d(x, y, z, my_data_grid)
The docs say:
If 4 arrays, (x, y, z, scalars) are passed, the 3 first arrays give
the position of the arrows, and the last the scalar value.
What are "the arrows"? I haven't found any examples and when I try to call it with my dataset I get a segfault so haven't been able to test.
EDIT: Well now I understand the format that mlab expects x, y, and z in and I was able to get it to work. However, there were no arrows! I'm assuming this is an error in the documentation...
It is not so much an error in the documentation, but more of a seemingly awkward way to describe the function. From the same document, contour3d:
Plots iso-surfaces for a 3D volume of data supplied as arguments
and it is stated that (bolding mine):
The x, y and z arrays are then supposed to have been generated by numpy.mgrid, in other words, they are 3D arrays, with positions lying on a 3D orthogonal and regularly spaced grid with nearest neighbor in space matching nearest neighbor in the array. The function builds a scalar field assuming the points are regularly spaced.
The 'arrows' seem to be a somewhat awkward way of saying that x, y and z are `
3D arrays, with positions lying on a 3D orthogonal and regularly
spaced grid
with the function 'building a scalar field' as an iso-surface, effectively 'connecting the dots (positions)'.

3D interpolation of 2 lists in python

hi i have two sets of data taken from two seperate import files which are both being imported into python and have been placed in two seperate lists as follows:
list 1 is of the form:
(node, x coordinate, y coordinate, z coordinate)
example list 1: [[1,0,0,0],[2,1,0,0],[3,0,1,0],[4,1,1,0],[5,0,0,1],[6,1,0,1],[7,0,1,1],[8,1,1,1]]
list 2 is in the form:
(x coordinate, y coordinate, z coordinate, temperature)
example list 2: [[0,0,0,100],[1,0,0,90],[0,1,0,85],[1,1,0,110],[0,0,1,115],[1,0,1,118],[0,1,1,100],[1,1,11,96]]
from these two lists I need to use the coordinates to create a third list which contains a node value and its corresponding temperature. This task is a simple dictionary function if all the x y and z coordinates match up however with the data i am working with this will not always be the case.
For example if in list 1 I add a new entry at the end of the list, node number 9;
new entry at end of list 1 [9, 0.5, 0.9, 0.25]
Now I find myself with a node number with no corresponding temperature. At this point an interpolation function will need to be performed on list 2 to give me the temperature related to this node. Through basic 3d interpolation calculations I have worked out that this temperature will be 97.9 therefore my final output list would look like this:
Output list:
(node, temperature)
Output list: [[1,100],[2,90],[3,85],[4,110],[5,115],[6,118],[7,100],[8,96],[9,97.9]]
I am reasonably new to python so am struggling to find a solution to this interpolation problem, I have been researching how to do this for a number of weeks now and have still not been able to find a solution.
Any help would be greatly greatly appreciated,
Thanks
There are quite a few interpolation routines in scipy, but above 2 dimensions, most of them only offer linear and nearest neighbour interpolation - which might not be sufficient for your use.
All of the interpolation routiens are listed on the interplation page of the scipy docs area. Straight away you can ignore the mnivariate, and 1D and 2D spline sections - you want the multivariate section.
There are 9 functions here, split into structured and unstructed data:
Unstructured data:
griddata(points, values, xi[, method, ...]) Interpolate unstructured
D-dimensional data.
LinearNDInterpolator(points, values[, ...]) Piecewise linear interpolant in N dimensions.
NearestNDInterpolator(points, values) Nearest-neighbour interpolation in N dimensions.
CloughTocher2DInterpolator(points, values[, tol]) Piecewise cubic, C1 smooth, curvature-minimizing interpolant in 2D.
Rbf(*args) A class for radial basis function approximation/interpolation of n-dimensional scattered data.
interp2d(x, y, z[, kind, copy, ...]) Interpolate over a 2-D grid. For >
data on a grid:
interpn(points, values, xi[, method, ...]) Multidimensional
interpolation on regular grids.
RegularGridInterpolator(points, values[, ...]) Interpolation on a regular grid in arbitrary dimensions
RectBivariateSpline(x, y, z[, bbox, kx, ky, s]) Bivariate spline approximation over a rectangular mesh.
plus an additional one in the see also section, though we'll ignore that.
You should read how they each work, it might help you understand a little better.
The way these functions work though, is that you pass them data i.e. x,y,z coords, and the corresponding values at those points, and they then return a function which allows you to get a point at any location.
I would recommend the Rbf function here though, as from what i can see it's the only nD option which does not limit you to linear or nearest neighbour interpolation.
For example, you have two lists:
node_locations = [(node, x_coord, y_coord, z_coord), ...]
temp_data = [(x0, y0, z0, temp0), (x1, y1, z1, temp1), ...]
xs, ys, zs, temps = zip(*teemp_data) # This will unpack your data into columns, rather than rows.
from scipy.interpolate import Rbf
rbfi = Rbf(xs, ys, zs, temps)
# I don't know how you want your output data, so i'm just dumping it in a dictionary.
node_data = {}
for node, x, y, z in node_locations:
node_data[node] = rbfi(x, y, z)
Try something like that.
For scientific computing, I wouldn't use lists but numpy arrays instead.
So in your case:
import numpy as np
nodes = np.array(example_list_1)
temperatures = np.array(example_list_2)
With this you can then go on to use scipy's interpolation functions, like for example:
http://docs.scipy.org/doc/scipy/reference/generated/scipy.interpolate.griddata.html#scipy.interpolate.griddata
from scipy.interpolate import griddata
interpolated = griddata(temperatures[:, :-1],
temperatures[:, -1],
nodes[:, 1:])

How to get X- oder Y-Coordinate from Scipy mathematical function

When I create a simple mathematical function like..
f(X) = 2*X
using scipy.interpolate - how can I get the X-coordinate of a corresponding Y-coordinate?
Here is the scipy-function:
from scipy import interpolate
testfunc = scipy.interpolate.interp1d([1,2], [2,4], kind='linear')
I want to get the X-value belonging to Y = 4 (should be 2).
I tried:
testfunc.x(4)
Would it work to just do reverse interpolation?
x,y = ...
testfunc_inverse = scipy.interpolate.interp1d(y, x, kind='linear')
testfunc_inverse(4)
I may be missing the point here, however, if you follow the scipy.interpolate.interp1d example you will end up with two numpy arrays of equal length. Seems like you should be able to index the y array against the x array and get your answer. I don't know if you would consider this approach 'pythonic' but it works in this case.

Categories