Python 在两个数据帧之间的每个数据点之间比较每个数据点,而不进行循环

Python 在两个数据帧之间的每个数据点之间比较每个数据点,而不进行循环,python,pandas,Python,Pandas,我想检查dataframe-1(df1)中的坐标(x,y,z),以查看该位置是否足够靠近一个不规则曲面,该曲面在dataframe-2(df2)中存储了自己的坐标(x,y,z) 我能够遍历df1中的每个坐标,然后遍历df2中的所有坐标并检查它的距离。然后对df1中的所有坐标重复此操作,但当我在df1中有超过1000000个坐标要检查时,这将需要很长时间 我正在使用熊猫,想知道它是否可以不用循环 如果df1中的坐标接近df2,那么我想选择它并将其存储到df3中。Scipy可以帮助您。请看以下假设示

我想检查dataframe-1(df1)中的坐标(x,y,z),以查看该位置是否足够靠近一个不规则曲面,该曲面在dataframe-2(df2)中存储了自己的坐标(x,y,z)

我能够遍历df1中的每个坐标,然后遍历df2中的所有坐标并检查它的距离。然后对df1中的所有坐标重复此操作,但当我在df1中有超过1000000个坐标要检查时,这将需要很长时间

我正在使用熊猫,想知道它是否可以不用循环


如果df1中的坐标接近df2,那么我想选择它并将其存储到df3中。

Scipy可以帮助您。请看以下假设示例:

import pandas as pd 
from scipy.spatial import cKDTree

dataset1 = pd.DataFrame(pd.np.random.rand(100,3))
dataset2 = pd.DataFrame(pd.np.random.rand(10, 3))

ck = cKDTree(dataset1.values)

ck.query_ball_point(dataset2.values, r=0.1)
数组([list([])、list([])、list([])、list([])、list([])、list([28,83]), 清单([79]), 列表([])、列表([86])、列表([40])、列表([29,60,95])、数据类型=对象)

使用Numpy方法:

如果您的两个数据帧如下所示:

df1
    coords
0   (4,3,5)
1   (5,4,3)

df2
    coords
0   (6,7,8)
1   (8,7,6)
然后:


您需要显示数据帧和预期输出。这样做更容易。df1=0.0112703-0.0343516-0.0138510.0110492-0.0343281-0.0136868-0.0108239-0.0342809-0.0134757 0.0105686-0.0342081-0.0132085 df2=nodenumber,x坐标,y坐标,z坐标1,2.5552903E-04-8.828905970E-02,-3.719565645E-02,2.4152590E-04,--48808-4802,-3.719100356E-023,3.034976253E-04,-8.874925971E-02,-3.717557713E-02…哇!谢谢:)我有大约100万个粒子,我在时间里跟踪它们,我想知道它们中是否有一个接近或通过不规则的表面,这是非常有效的。
import numpy as np
from itertools import product

#convert dataframes into numpy arrays
df1_arr = np.array([np.array(x) for x in df1.coords.values])
df2_arr = np.array([np.array(x) for x in df2.coords.values])

#create array of cartesian product of elements of the two arrays
cart_arr = np.array([x for x in product(df1_arr,df2_arr)])

#compute Euclidian distance (or norm) between pairs of elements in two arrays
#outputs new array with one value per pair of coordinates
norms_arr = np.linalg.norm(np.diff(cart_arr,axis=1)[:,0,:],axis=1)

#create distance threshold for "close enough"
radius = 5.5

#find values in norms array that are less than or equal to distance threshold
good_idxs = np.argwhere(norms_arr <= radius)[:,0]
good_coord_pairs = cart_arr[good_idxs]

#store corresponding pairs of coordinates and distances in new dataframe
final_df = pd.DataFrame({'df1_coords':list(map(tuple,good_coord_pairs[:,0,:])),
   'df2_coords':list(map(tuple(good_coord_pairs[:,1,:])), 'distance':norms_arr[good_idxs],
   index=list(range(len(good_coord_pairs))))
final_df
    df1_coords  df2_coords  distance
0   (4,3,5)     (6,7,8)     5.385165
1   (5,4,3)     (8,7,6)     5.196152