我可以使用lambda、map、apply或applymap来填充数据框吗?

3
这是我的数据的简化版本。我有一个坐标的数据框和一个空的数据框,应该使用提供的函数来填充每一对的距离。
有什么最快的方法来填充这个数据框?尽可能地避免嵌套for循环(慢!)。我可以使用apply或applymap吗?您可以相应地修改函数或其他部分。谢谢。
import pandas as pd

def get_distance(point1, point2):
    """Gets the coordinates of two points as two lists, and outputs their distance"""
    return (((point1[0] - point2[0]) ** 2 + (point1[1] - point2[1]) ** 2 + (point1[2] - point2[2]) ** 2) ** 0.5)

#Dataframe of coordinates.    
df = pd.DataFrame({"No.": [25, 36, 70, 95, 112, 101, 121, 201], "x": [1,2,3,4,2,3,4,5], "y": [2,3,4,5,3,4,5,6], "z": [3,4,5,6,4,5,6,7]})
df.set_index("No.", inplace = True)

#Dataframe to be filled with each pair distance.
df_dist = pd.DataFrame({'target': [112, 101, 121, 201]}, columns=["target", 25, 36, 70, 95])
df_dist.set_index("target", inplace = True)
2个回答

0

如果您不想使用for循环,可以按照以下方式计算所有可能的点对之间的距离。

首先,您需要对df进行笛卡尔积,以获得所有可能的点对。

i, j = np.where(1 - np.eye(len(df)))
df=df.iloc[i].reset_index(drop=True).join(
    df.iloc[j].reset_index(drop=True), rsuffix='_2')

其中ij是大小为len(df)的方阵的上三角和下三角的布尔索引。完成此操作后,您只需要应用您的距离函数即可。

df['distance'] = get_distance([df['x'],df['y'],df['z']], [df['x_2'],df['y_2'],df['z_2']])
df.head()

No. x   y   z   No._2   x_2 y_2 z_2 distance
0   25  1   2   3   36  2   3   4   1.732051
1   25  1   2   3   70  3   4   5   3.464102
2   25  1   2   3   95  4   5   6   5.196152
3   25  1   2   3   112 2   3   4   1.732051
4   25  1   2   3   101 3   4   5   3.464102

如果您只想计算 df_dist 中的点,则可以相应地修改矩阵 1 - np.eye(len(df))

0

据我所知,使用lambda表达式并没有比for循环更快的明显优势 - 而且编写双重lambda表达式非常困难,通常这仅用于简单的行操作。

然而,通过一些工程技巧,我们可以将代码简化为几行简单易懂的语句:

import numpy as np

get = lambda i: df.loc[i,:].values
dist = lambda i, j: np.sqrt(sum((get(i) - get(j))**2))
# Fills your df_dist
for i in df_dist.columns:
    for j in df_dist.index:
        df_dist.loc[j,i] = dist(i, j)

生成的 df_dist

              25        36        70        95
target                                        
112     1.732051  0.000000  1.732051  3.464102
101     3.464102  1.732051  0.000000  1.732051
121     5.196152  3.464102  1.732051  0.000000
201     6.928203  5.196152  3.464102  1.732051

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接