从宇宙学对象之间的距离构建邻接矩阵

Build an adjacency matrix from distances between cosmological objects

我正在探索 Illustris API,并从特定的宇宙模拟中收集给定红移值的信息。

这就是我请求 api:

import requests

baseUrl = 'http://www.tng-project.org/api/'
    
def get(path, params=None):
    # make HTTP GET request to path
    headers = {"api-key":"my_key"}
    r = requests.get(path, params=params, headers=headers)

    # raise exception if response code is not HTTP SUCCESS (200)
    r.raise_for_status()

    if r.headers['content-type'] == 'application/json':
        return r.json() # parse json responses automatically
    
    if 'content-disposition' in r.headers:
        filename = r.headers['content-disposition'].split("filename=")[1]
        with open(f'sky_dataset/simulations/{filename}', 'wb') as f:
            f.write(r.content)
        return filename # return the filename string
    return r

下面我得到了这个特定模拟中给定子晕的恒星坐标。请注意 - 如果我做对了 - 距离已经从 ckpc/h 转换为 physical kpc.

物理坐标是您在冻结 space 并开始布置测量杆时测量的实际距离:

import h5py
import numpy as np

simulation_id = 100
redshift = 0.57
subhalo_id = 99

scale_factor = 1.0 / (1+redshift)
little_h = 0.704

params = {'stars':'Coordinates,GFM_Metallicity'}

url = "http://www.tng-project.org/api/Illustris-1/snapshots/z=" + str(redshift) + "/subhalos/" + str(subhalo_id)
sub = get(url) # get json response of subhalo properties
saved_filename = get(url + "/cutout.hdf5",params) # get and save HDF5 cutout file

with h5py.File(f'sky_dataset/simulations/{saved_filename}') as f:
    # NOTE! If the subhalo is near the edge of the box, you must take the periodic boundary into account! (we ignore it here)
    dx = f['PartType4']['Coordinates'][:,0] - sub['pos_x']
    dy = f['PartType4']['Coordinates'][:,1] - sub['pos_y']
    dz = f['PartType4']['Coordinates'][:,2] - sub['pos_z']
    
    rr = np.sqrt(dx**2 + dy**2 + dz**2)
    rr *= scale_factor/little_h # ckpc/h -> physical kpc

    fig = plt.figure(figsize=(12,12))
    with mpl.rc_context(rc={'axes3d.grid': True}):
        ax = fig.add_subplot(projection='3d')

        # Plot the values
        ax.scatter(dx, dy, dz)
        ax.set_xlabel('X-axis')
        ax.set_ylabel('Y-axis')
        ax.set_zlabel('Z-axis')
    plt.show()

以上地块:

应一位评论的要求,我打印了 dy、dy、dz 截断示例:

dx = [ 2.63370612e-01  3.48350511e-01 -1.23379511e-02 ...  6.63767411e+00
  1.32910697e+01  8.75469902e+00]

dy = [  0.33889825   0.21808108   0.50170807 ...   8.95542985  -9.84251952
 -16.38661054]

dz = [ -0.26469788  -0.10382767  -0.16625317 ...  -4.84708218 -13.77888398
  10.42730599]

我的目标是为这个系统建立一个连接网络,从一个正方形(对称)邻接矩阵开始,其中任何两个星(或顶点)如果位于链接长度内则连接 l 1.2 Mpc,即:

Aij = 1 if rij ≤ l, otherwise 0

其中rij是两个顶点之间的距离,ij.

如何根据我的链接长度得到这个邻接矩阵?

使用 sklearn.neighbors.radius_neighbors_graph 和您的示例数据的解决方案:

from sklearn.neighbors import radius_neighbors_graph

# Your example data in runnable format
dx = np.array([2.63370612e-01, 3.48350511e-01, -1.23379511e-02, 
               6.63767411e+00, 1.32910697e+01,  8.75469902e+00])
dy = np.array([0.33889825,  0.21808108,   0.50170807, 
               8.95542985, -9.84251952, -16.38661054])
dz = np.array([-0.26469788,  -0.10382767, -0.16625317, 
               -4.84708218, -13.77888398, 10.42730599])

# Build a coordinate matrix with columns x, y, z, with one star per row
X = np.column_stack([dx, dy, dz])

print(X)
[[ 2.63370612e-01  3.38898250e-01 -2.64697880e-01]
 [ 3.48350511e-01  2.18081080e-01 -1.03827670e-01]
 [-1.23379511e-02  5.01708070e-01 -1.66253170e-01]
 [ 6.63767411e+00  8.95542985e+00 -4.84708218e+00]
 [ 1.32910697e+01 -9.84251952e+00 -1.37788840e+01]
 [ 8.75469902e+00 -1.63866105e+01  1.04273060e+01]]

# Find the neighbours of each star, restricted to distance lower than radius=1.2
C = radius_neighbors_graph(X, 1.2)

# C is the connectivity matrix in Compressed Sparse Row (CSR) format. 
# For demonstration purposes, convert CSR matrix to dense representation 
# as a numpy matrix
C.todense()

matrix([[0., 1., 1., 0., 0., 0.],
        [1., 0., 1., 0., 0., 0.],
        [1., 1., 0., 0., 0., 0.],
        [0., 0., 0., 0., 0., 0.],
        [0., 0., 0., 0., 0., 0.],
        [0., 0., 0., 0., 0., 0.]])

对于您的六颗星的示例数据,连接矩阵显示:

  • Star 0(第 0 行)在 Stars 1 和 2 的 1.2 个距离单位 (kpc) 内
  • 1 星和 2 星之间的距离在 1.2 kpc 以内

(你要求链接距离为1.2Mpc,对应radius=1200。为了演示,这里我使用了radius=1.2,对应1.2kpc,因为所有六颗星都在 1.2 Mpc 以内,这会导致一个相当乏味的连接矩阵。)