You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何对两个Pandas DataFrame的行执行外积运算?

Pandas 实现两个DataFrame全行列对应乘积并保留标签

问题描述

有两个列标签完全一致的Pandas DataFrame,列包含label、data1、data2……dataN。需要对两个DataFrame的所有行组合进行对应数据列的乘积运算(即data1与data1相乘、data2与data2相乘等),并在结果DataFrame中保留两个原DataFrame的label列。

示例数据

Frame 1

labeld1d2d3
a123
b456

Frame 2

labeld1d2d3
c789
d101112

期望结果

label_1label_2d1d2d3
ac71627
ad102236
bc284054
bd405572

最优实现方案

不需要用低效的循环,利用Pandas的笛卡尔积合并结合广播乘法就能高效完成,以下是两种可行方案:

方案一:基于Pandas合并的常规写法

import pandas as pd

# 构造示例数据
df1 = pd.DataFrame({'label': ['a', 'b'], 'd1': [1,4], 'd2': [2,5], 'd3': [3,6]})
df2 = pd.DataFrame({'label': ['c', 'd'], 'd1': [7,10], 'd2': [8,11], 'd3': [9,12]})

# 重命名label列,避免合并冲突
df1 = df1.rename(columns={'label': 'label_1'})
df2 = df2.rename(columns={'label': 'label_2'})

# 添加临时键生成笛卡尔积
df1['key'] = 1
df2['key'] = 1
cartesian_df = pd.merge(df1, df2, on='key').drop('key', axis=1)

# 获取数据列名
data_cols = [col for col in df1.columns if col not in ['label_1', 'key']]

# 对应列相乘
cartesian_df[data_cols] = cartesian_df[[f'{col}_x' for col in data_cols]] * cartesian_df[[f'{col}_y' for col in data_cols]]

# 清理多余列
cartesian_df = cartesian_df.drop([col for col in cartesian_df.columns if '_x' in col or '_y' in col], axis=1)

print(cartesian_df)

方案二:基于Numpy广播的高效写法(内存更友好)

适合数据量较大的场景,直接用Numpy广播完成乘积运算,减少中间列的生成:

import pandas as pd
import numpy as np

# 构造示例数据
df1 = pd.DataFrame({'label': ['a', 'b'], 'd1': [1,4], 'd2': [2,5], 'd3': [3,6]})
df2 = pd.DataFrame({'label': ['c', 'd'], 'd1': [7,10], 'd2': [8,11], 'd3': [9,12]})

# 重命名label列
df1 = df1.rename(columns={'label': 'label_1'})
df2 = df2.rename(columns={'label': 'label_2'})

# 提取数据部分并做广播乘积
df1_data = df1.drop('label_1', axis=1).to_numpy()[:, None, :]
df2_data = df2.drop('label_2', axis=1).to_numpy()[None, :, :]
product_data = (df1_data * df2_data).reshape(-1, df1_data.shape[-1])

# 生成标签的笛卡尔积
labels = pd.merge(df1[['label_1']].assign(key=1), df2[['label_2']].assign(key=1), on='key').drop('key', axis=1)

# 合并标签与乘积结果
result_df = pd.concat([labels, pd.DataFrame(product_data, columns=df1.drop('label_1', axis=1).columns)], axis=1)

print(result_df)

两种方案都能得到符合要求的结果,其中方案二的内存开销更小,运算效率更高。

内容的提问来源于stack exchange,提问作者Immot

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.15 12:30:48