Numpy 使用(mayavi)mlab.contour3d打印存储在文件中的数据?

Numpy 使用(mayavi)mlab.contour3d打印存储在文件中的数据?,numpy,mayavi,mayavi.mlab,Numpy,Mayavi,Mayavi.mlab,我正在努力使用从文件中读取的数据在mayavi中绘制一个简单的contour3d绘图。数据是格式为的规则三维笛卡尔网格 x1 y1 z1 val(x1,y1,z1) x1 y1 z2 val(x1,y1,z2) . . . . x1 y1 z_K val(x1,y1,z_K) x1 y2 z1 val(x1,y2,z1) . . .

我正在努力使用从文件中读取的数据在mayavi中绘制一个简单的contour3d绘图。数据是格式为的规则三维笛卡尔网格

   x1   y1    z1    val(x1,y1,z1)  
   x1   y1    z2    val(x1,y1,z2)  
    .    .     .       .  
   x1   y1     z_K  val(x1,y1,z_K)  

   x1   y2     z1    val(x1,y2,z1)  
    .    .     .       .  
    .    .     .       .  
   x_L   y_M    z_K    val(x_L,y_M,z_K)  
(这里每行的前3个值给出点的(x,y,z)坐标,第4个值给出该点的标量值。如果有用,我可以粘贴一个最小的示例文件)

可以使用numpy.loadtxt成功读入数据文件,但如何从中获取数据 使用(mayavi)mlab.contour3d绘制等值面图?我认为默认输出 loadtxt中的数组的格式不适合mlab.contour3d

我能找到的所有mlab.contour3d示例都使用ogrid生成一个网格,然后绘制该网格的一个简单函数(sin等)。我已经成功地运行了这些示例,但它们没有告诉我如何将文件中的数据读入正确的格式
已准备好打印的阵列。我相信,如果有人能给我一个指针,它会帮助很多处于类似位置的新手;绘制存储在另一个程序生成的文件中的三维数据肯定是科学家必须完成的最常见的绘制任务之一。

为延迟响应向E先生道歉,我周末没有上网。 然而,我确实可以使用计算机,我找到了我问题的答案,尽管有点难看。我确信以下方法可以改进,并且,基于上述原因,我知道这是3d绘图软件的一个重要基本用途,因此,如果任何人有任何改进,他们将不胜感激。下面的解释假设您使用的是Linux,但我相信在其他操作系统上执行相同的操作(即保存和运行python文件)也很简单

首先生成样本数据文件。实际数据来自Fortran程序,但出于当前测试目的,我将使用python生成一个示例数据文件。将以下代码存储在文件“gen data.py”中(将粘贴复制到您最喜欢的文本编辑器中,然后单击“另存为”等)

使用以下命令运行程序: python gen-data.py>stream.out 它将在数据文件“stream.out”中存储上述类型的示例数据文件。您应该有一个值为的文件:
-1.0-2.0-3.0 14.0
-1.0-2.0.0.5.0
-1.0-2.0 3.0 14.0
-1.0 0.0-3.0 10.0
-1.0 0.0 0.0 1.0
-1.0 0.0 3.0 10.0
-1.02.0-3.014.0
-1.0 2.0 0.0 5.0
-1.0 2.0 3.0 14.0
-0.5-2.0-3.0 13.25
. . . .
0.52.03.013.25
1.0-2.0-3.0 14.0
1.0-2.0.0.5.0
1.0-2.0 3.0 14.0
1.0 0.0-3.0 10.0
1.0 0.0 0.0 1.0
1.0 0.0 3.0 10.0
1.02.0-3.014.0
1.0 2.0 0.0 5.0
1.0 2.0 3.0 14.0
数据文件中的每一行的格式为
xyzv(x,y,z)
其中x,y,z表示空间中某点的x,y,x坐标,V(x,y,z)表示 该点的标量值

绘制数据
我们的问题是如何使用mayavi绘制这些数据-我特别感兴趣 在绘制等值面时,可使用contour3d命令实现。 web上的众多示例显示了生成的contour3d绘图数据 使用mgrid命令。(也有使用ogrid命令的示例,但是 对我来说,mgrid更容易理解)。策略:如果我们可以操纵数据,使其具有与mgrid命令输出相同的形状和来源,那么我们应该能够绘制它。 通过分析mgrid的输出,很明显所需的是三维的 用于存储x、y和z坐标的numpy数组,以及另一个三维numpy数组 在这些点上存储标量值(上面的V)。以下程序 实现这些步骤。我认为该计划肯定可以改进: 我敢肯定,常规的填充数组可以被一行程序所取代,由 了解python中的数组切片,可能还有其他地方 有待改进。我忍不住想,对于那些知道他们在numpy/mayavi做什么的人来说,整个事情可能可以用一两行来完成,但是下面 我相信,这个程序很容易理解,而且很有效(你们应该看到) 显示的绘图中的曲面)。
将以下文件保存到“hope.py”并使用运行
python hope.py

import numpy
from mayavi import mlab

def fill_up_array(output_arr,source_arr,nx,ny,nz,posn):
# takes a slice of results from source_arr and writes to output_arr
# there is probably an easy one liner to do this ?
#TODO: add checks to ensure input is sensible
    for i in range(nx):
        for j in range(ny):
            for k in range(nz):
                output_arr[i][j][k] = source_arr[i][j][k][posn]

# these numbers have to correspond to those used in gen-data.py
NX = 5 ; NY = 3 ; NZ = 3 

NDIM = 4  # number of columns in data file, 4 for current example


#initialise arrays:
# xx will contain x coordinate of data point
# yy will contain y coordinate of data point
# zz will contain z coordinate of data point
# VV will contain sample scalar value at (x,y,z)
xx = numpy.zeros((NX,NY,NZ))
yy = numpy.zeros((NX,NY,NZ))
zz = numpy.zeros((NX,NY,NZ))
VV =  numpy.zeros((NX,NY,NZ))


#now read in values from stream.out file to these arrays
full = numpy.loadtxt("stream.out")
fy = numpy.reshape(full, (NX,NY,NZ,NDIM))


fill_up_array(xx,fy,NX,NY,NZ,0)
fill_up_array(yy,fy,NX,NY,NZ,1)
fill_up_array(zz,fy,NX,NY,NZ,2)
fill_up_array(VV,fy,NX,NY,NZ,3)


#test plot
mlab.contour3d(xx, yy, zz, VV)
mlab.show()

我发现以下方法很有效

x、 y,z,d是原始输入文本文件中的一维numpy数组,其中d=f(x,y,z)


如果您可以添加一些示例数据(例如,数据文件中的几行)和读取该文件的代码,则会有所帮助。然后,人们可以向您展示如何从这一点转变为有效的解决方案。
import numpy
from mayavi import mlab

def fill_up_array(output_arr,source_arr,nx,ny,nz,posn):
# takes a slice of results from source_arr and writes to output_arr
# there is probably an easy one liner to do this ?
#TODO: add checks to ensure input is sensible
    for i in range(nx):
        for j in range(ny):
            for k in range(nz):
                output_arr[i][j][k] = source_arr[i][j][k][posn]

# these numbers have to correspond to those used in gen-data.py
NX = 5 ; NY = 3 ; NZ = 3 

NDIM = 4  # number of columns in data file, 4 for current example


#initialise arrays:
# xx will contain x coordinate of data point
# yy will contain y coordinate of data point
# zz will contain z coordinate of data point
# VV will contain sample scalar value at (x,y,z)
xx = numpy.zeros((NX,NY,NZ))
yy = numpy.zeros((NX,NY,NZ))
zz = numpy.zeros((NX,NY,NZ))
VV =  numpy.zeros((NX,NY,NZ))


#now read in values from stream.out file to these arrays
full = numpy.loadtxt("stream.out")
fy = numpy.reshape(full, (NX,NY,NZ,NDIM))


fill_up_array(xx,fy,NX,NY,NZ,0)
fill_up_array(yy,fy,NX,NY,NZ,1)
fill_up_array(zz,fy,NX,NY,NZ,2)
fill_up_array(VV,fy,NX,NY,NZ,3)


#test plot
mlab.contour3d(xx, yy, zz, VV)
mlab.show()
# Import relevant modules
import numpy as np
import scipy.interpolate as si
from mayavi import mlab

# Generate the figure
figure = mlab.figure()

# Generate the 3D mesh
xi, yi, zi = np.meshgrid(*([np.linspace(0,1,100)] * 3))

# Interpolate d over the 3D mesh
di = si.griddata((x, y, z), d, (xi, yi, zi))

# Generate the desired figure
min_d = d.min()
max_d = d.max()
grid = mlab.pipeline.scalar_field(di)
mlab.pipeline.volume(grid, vmin=min_d, vmax=min_d + .5*(max_d-min_d))

# Other good options too
## mlab.contour3d(di, vmin=min_d, vmax=min_d + .8*(max_d-min_d))
## pts = mlab.points3d(x, y, z, d)
mlab.axes()
mlab.show()