簡體   English   中英

Matplotlib -3D 數據可視化

[英]Matplotlib -3D data visualization

這是一個 txt 文件的示例

我的實驗測量是在幾個txt文件中(實際上我會有數百個文件,但為了演示繪圖的想法,這里我只列出了3個文件,它們是d_401.txt、d_402.txt、d_403.txt)每個文件有 4 列和 256 行數據。 (只有第一列和第四列是我需要的 x 和 z 數據)

我想從這些文件中繪制 3D 曲面圖/或等高線圖。 在我的 3D 圖中,x 軸通常是每個文件的第 1 列數據,z 軸是每個文件的第 4 列數據(z 值也需要在漸變中進行顏色編碼),最后 y 軸是“從這三個文件中繪制的所有 xz 值的“y 方向排列”。

如何為這個圖生成 python 代碼? 我特別困惑如何分配矩陣 Z,如果有人能在這個問題上幫助我,我將不勝感激......我需要盡快繪制該圖。

我附上了我的早熟(據說全是錯誤代碼)

太感謝了!!!

import numpy as np
from matplotlib import pyplot as plt
from mpl_toolkits.mplot3d import Axes3D
from matplotlib import cm

fig = plt.figure()
ax = fig.add_subplot(111, projection='3d')

z_txt = np.array(['d_401.txt', 'd_402.txt', 'd_403.txt'])

zarray = np.zeros([z_txt.size])
y = np.arange(3)
x = np.zeros(256)
Z = np.zeros((len(y),len(x)))


for i in range(z_txt.size):
    zarray[i] = np.loadtxt(z_txt[i])
    x[i] = zarray[i,0]
    X, Y = np.meshgrid(x,y)
    Z[i] = zarray[i,3]
ax.plot_surface(X, Y, Z, cmap=cm.magma, shade=True, lw=3)

plt.show()

以下假設所有文件都包含相同的x向量……

In [146]: import numpy as np
     ...: import matplotlib.pyplot as plt
     ...: from matplotlib.cm import ScalarMappable as sm
     ...: from glob import glob
     ...: 
     ...: # create fake data and put it in files
     ...: x0, y0 = np.arange(11.0), np.arange(3)+1.0
     ...: z0 = x0+y0[:,None]
     ...: for i in range(3):
     ...:     with open('delendo%d'%(i+1), 'w') as out:
     ...:         for x0z0 in zip(x0, x0+x0, x0-x0, z0[i]):
     ...:             print(*x0z0, sep='\t', file=out)
     ...: 
     ...: # sorted list of "interesting" files
     ...: files = sorted(glob('delendo*'))
     ...: 
     ...: # read the matrix of z values
     ...: Z = np.array([np.loadtxt(f, usecols=3) for f in files])
     ...: # read the vector of x values (the same for all files, I hope so!)
     ...: x = np.loadtxt(files[0], usecols=0)
     ...: # we have as many y's as rows in Z, and we count from 1
     ...: y = np.arange(Z.shape[0])+1
     ...: 
     ...: # prepare for a 3D plot and plot as a surface
     ...: fig, ax = plt.subplots(constrained_layout=1,
     ...:                        subplot_kw={"projection" : "3d"})
     ...: surf = ax.plot_surface(*np.meshgrid(x,y), Z, cmap='magma')
     ...: norm = plt.Normalize(*surf.get_clim())
     ...: plt.colorbar(sm(norm=norm, cmap='magma'))
     ...: plt.show()

在此處輸入圖片說明


附錄

解決 OP 評論中提出的一些問題

您詢問*sequence運算符。 它是解包運算符,可以在賦值或表達式中使用。 讓我們來看看

>>> tup = (1,2,3,4,5)
>>> a = tup ; print(a)
(1, 2, 3, 4, 5)
>>> a, b = tup
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
ValueError: too many values to unpack (expected 2)

但是如果你使用 unpack 操作符

>>> a, *b = tup ; print(a, b)
1 [2, 3, 4, 5]

Python中了解到, b是該序列的其余元素的順序和商店tup -順便說一句, b是一個列表不是一個元組。

unpack 操作符可以用在 left 成員的中間,但只能使用一次,因為 Python 將剩余的內容分配給帶星號的項目,而兩個帶星號的項目會導致歧義。

>>> a,*b, c = tup ; print(a, b, c)
1 [2, 3, 4] 5
>>> a,*b, *c = tup ; print(a, b, c)
  File "<stdin>", line 1
SyntaxError: multiple starred expressions in assignment

現在,讓我們看看解包運算符在表達式中的作用

>>> print(*b)
2 3 4 

使用星號語法解壓列表,就像

>>> print(b[0], b[1], b[2])
2 3 4

現在,回到您的問題,您已經在代碼中使用了解包。 即使你可能不知道它......

    X, Y = np.meshgrid(x,y)

來到我的代碼

surf = ax.plot_surface(*np.meshgrid(x,y), Z, cmap='magma')

在這一點上應該很清楚,我們正在解包meshgrid返回的meshgrid ,就像X, Y = meshgrid(...) ; surf = ...(X, Y, Z, ...) X, Y = meshgrid(...) ; surf = ...(X, Y, Z, ...)具有(小)優勢,即不引用網格數組 ( X, Y ) 並且它們使用的內存可以立即返回給解釋器。

關於您的最后一點,要創建顏色條 Matplotlib 需要所謂的標量可映射(sm),並且plt.colorbar可以檢查活動軸以查看是否有 sm 掛在附近。
許多藝術家(繪制到 Axes 中的軟件代理)例如imshow創建一個 sm 並且一切正常,但plot_surface不會,因此可憐的程序員必須為colorbar提供一個手工制作的 sm 。
要指定 sm,我們需要 ① 范數和 ② 顏色圖。
規范是默認值,即plt.Normalize ,我們需要Z的限制,這些是surf.get_clim()的值,我再次使用帶星號的語法來解壓這兩個值。

這個解釋的長度是首先省略它的理由......

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM