使用Pandas为现有DataFrame循环添加行未生效,求正确实现方法
解决Pandas添加新行保留原数据的问题
嘿,我来帮你搞定这个问题!你的代码没达到预期效果,主要是因为几个小细节没处理对:你没有真正新增行,只是在覆盖原DataFrame的列值,而且循环范围和价格计算的符号也有点小差错。
原代码的问题分析
- 没有新增行,仅覆盖列值:你在循环里执行
df_merged['price_new'] = ...时,是给整个price_new列赋值,而不是为每个true_move生成新行。循环结束后,你的DataFrame还是只有原来的1行,列值保留的是最后一次循环的结果。 - range范围不完整:
range((row['max_move_%']) * (-1), row['max_move_%'])会生成从-10到9的整数(不包含10),漏掉了你想要的true_move=10的情况。 - 价格计算符号与预期不符:你期望
true_move=-10对应price_new=90,但原代码中1 - a/100当a=-10时,计算结果是1.1,得到的是110,和你的预期对应关系相反。
正确的解决方案
方法一:用列表收集新行(直观易懂)
先遍历原数据的每一行,再遍历每个true_move值,把每一行的原始数据+新字段组成字典存入列表,最后转成DataFrame:
import pandas as pd # 你的原始数据 df_merged = pd.DataFrame({ 'product': [1], 'price': [100], 'max_move_%': [10] }) # 创建空列表存储所有新行 new_rows = [] for _, row in df_merged.iterrows(): product = row['product'] base_price = row['price'] max_move = row['max_move_%'] # 遍历从 -max_move 到 max_move 的所有整数(包含两端) for true_move in range(-max_move, max_move + 1): # 计算符合预期的新价格 price_new = base_price * (1 + true_move / 100.0) # 构造新行,保留原列并新增字段 new_row = { 'product': product, 'price': base_price, 'max_move_%': max_move, 'true_move': true_move, 'price_new': price_new } new_rows.append(new_row) # 转成最终的DataFrame result_df = pd.DataFrame(new_rows) print(result_df)
运行后你会得到21行数据(从true_move=-10到10),每个行都保留了原数据的字段,同时新增了true_move和price_new。
方法二:用Pandas内置方法(更高效)
如果你的数据量较大,推荐用apply+explode的方式,避免纯Python循环的性能问题:
import pandas as pd df_merged = pd.DataFrame({ 'product': [1], 'price': [100], 'max_move_%': [10] }) # 为每一行生成true_move的列表 df_merged['true_move'] = df_merged['max_move_%'].apply(lambda x: list(range(-x, x + 1))) # 把列表展开成多行 df_expanded = df_merged.explode('true_move', ignore_index=True) # 计算price_new df_expanded['price_new'] = df_expanded['price'] * (1 + df_expanded['true_move'] / 100.0) print(df_expanded)
这个方法和方法一的结果完全一致,但处理大数据时速度会快很多。
内容的提问来源于stack exchange,提问作者HeadOverFeet
相关产品推荐
相关产品推荐

