簡體   English   中英

將坐標元組信息轉換為numpy數組

[英]Converting coordinate tuple information to numpy arrays

我得到了有限元程序的結果,該程序在三維空間中的規則間隔的網格位置處給出各種感興趣的測量值(例如,溫度,密度,壓力)。

值沿每個坐標等距離間隔,但對於不同的坐標,該間距可能不同。 例如,

x1 = [0, 0.1, 0.2, ..., 1.0]      (a total of NX1 pts) 
x2 = [0, 0.5, 1.0, ..., 20]       (a total of NX2 pts) 
x3 = [0, 0.2, 0.4, ..., 15]       (a total of NX3 pts)

軟件輸出的結果如下:

x1_1, x2_1, x3_1, f_x, g_x, h_x
x1_1, x2_1, x3_2, f_x, g_x, h_x
x1_1, x2_1, x3_3, f_x, g_x, h_x
...
x1_1, x2_2, x3_1, f_x, g_x, h_x
x1_1, x2_2, x3_2, f_x, g_x, h_x
x1_1, x2_2, x3_3, f_x, g_x, h_x
...
x1_2, x2_1, x3_1, f_x, g_x, h_x
x1_2, x2_1, x3_2, f_x, g_x, h_x
x1_2, x2_1, x3_3, f_x, g_x, h_x
...

其中f_x,g_x,h_x是特定網格點的感興趣度量。

我想轉換上面的數據格式並獲得f,g和h的(NX1 x NX2 x NX3)numpy數組。

一些結果集相當大(80 x 120 x 100)。

有沒有人有任何提示以有效的方式進行這種轉換?

假設您將整個數組作為形狀的數組data (Nx1 * Nx2 * Nx3, 6)讀入內存。

data = np.loadtxt('data.txt', dtype=float, delimiter=',')

如果,如您的示例所示,這些點是按字典順序生成的,您只需要將列抓取到fgh並重新整形:

f = data[:, 3].reshape(Nx1, Nx2, Nx3)
g = data[:, 4].reshape(Nx1, Nx2, Nx3)
h = data[:, 5].reshape(Nx1, Nx2, Nx3)

如果你需要弄清楚Nx1Nx2Nx3是什么,你可以使用np.unique

Nx1 = np.unique(data[:, 0]).shape[0]
Nx2 = np.unique(data[:, 1]).shape[0]
Nx3 = np.unique(data[:, 2]).shape[0]

如果無法保證點的順序,則可以使用np.unique將索引提取到網格值,這是一個更強大的解決方案:

Nx1, idx1 = np.unique(data[:, 0], return_inverse=True)
Nx1 = Nx1.shape[0]
Nx2, idx2 = np.unique(data[:, 1], return_inverse=True)
Nx2 = Nx2.shape[1]
Nx3, idx3 = np.unique(data[:, 2], return_inverse=True)
Nx3 = Nx3.shape[0]

f = np.empty((Nx1, Nx2, Nx3))
f[idx1, idx2, idx3] = data[:, 3]
g = np.empty((Nx1, Nx2, Nx3))
g[idx1, idx2, idx3] = data[:, 4]
h = np.empty((Nx1, Nx2, Nx3))
h[idx1, idx2, idx3] = data[:, 5]

這將為fgh創建新數組,而不是原始data數組的視圖,因此它將使用更多內存。

當然,不是上面重復所有內容的丑陋代碼,你應該使用循環或列表理解!

無論如何都必須循環遍歷整個文件,為什么不只是初始化數組並輸入值?

棘手的部分是,如果你想要一個具有形狀的數組(NX1,NX2,NX3) ,但如果你的x1,x2,x3值是float ,那么你必須以某種方式索引你的數組。 也許存在一個數據結構,但你可以使用類似的東西

def xyz_index((x,y,z),(n1,n2,n3)):
    """ return integer indices for x,y,z position
        given a constant step """
    return tuple(map(int,[x/n1,y/n2,z/n3]))

import numpy as np
NX1,NX2,NX3 =  (80, 120, 100)
ns = n1, n2, n3 =   (.1,.5,.2)
x1, x2, x3 = np.arange(0,1+n1,n1), np.arange(0,20+n2,n2), np.arange(0,15+n3,n3),

data = np.empty((NX1,NX2,NX3),dtype=[('f',float),('g',float),('h',float)])
with open(filename,'r') as f:
    for line in f:
        x,y,z,f,g,h = map(float,line.split(', '))
        data[xyz_index((x,y,z),ns)] = (f,g,h)

然后您可以按如下方式訪問您的數據:

對於點x1,x2,x3 = .2, .5, 0.處的hx1,x2,x3 = .2, .5, 0. ,使用

data[xyz_index((.2,.5,0),ns)]['h']

如果沒有['h'] ,這將返回帶有上述dtype(f,g,h)元組。

如果沒有索引,它將返回所有h(NX1,NX2,NX3)數組。


現在我看一下,如果n1, n2, n3總是相同的,你可能想 xyz_index函數中定義它們,那么你就不必每次都傳遞ns

data[xyz_index(.2,.5,0)]['h']

暫無
暫無

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

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