pandas嵌套循环修改行时触发DataFrame切片副本赋值警告如何解决
问题原因
警告触发的核心是你通过a.iloc[ind:(ind+len(z)), :]切出子DataFrame赋值给b时,pandas无法确定b是原DataFrame的视图还是独立副本,后续对b['a'].iloc[fraction]赋值时就会触发切片副本警告。你之前给b.copy()没用是因为警告是在修改b的阶段触发的,不是把b赋值回a的阶段。
方案选择建议
针对你提到的三个方案:
- 不建议直接抑制警告:当前版本下你的逻辑结果是对的,但pandas后续版本可能调整切片的视图/副本判定逻辑,会导致结果不符合预期,存在不可复现风险
- 转numpy数组操作可行,但需要单独处理非数值列的对应关系,反而增加代码复杂度,没必要完全更换架构
- 不需要用
append或者额外的copy操作,只要调整赋值逻辑,直接修改原DataFrame的对应位置即可彻底解决警告
修改后的可用代码
import pandas as pd a = pd.DataFrame( { 'a':[x/2 for x in range(1,11)], 'b':['hot dog', 'slider', 'watermelon', 'funnel cake', 'cotton candy', 'lemonade', 'fried oreo', 'ice cream', 'corn', 'sausage'], 'c':['meat', 'meat', 'vegan', 'vegan', 'vegan', 'vegan', 'dairy','dairy', 'vegan', 'meat'] } ) print(a) z = [x/(x+2) for x in range(1,5)] print(z) # 外层循环逐行遍历 for ind, row in a.iterrows(): # 计算当前可修改的最大行数,避免索引越界 loop = min(len(z), len(a) - ind) # 直接修改原DataFrame对应位置,不需要中间切片变量 for fraction in range(loop): a.loc[ind + fraction, 'a'] *= z[fraction] print(a)
调整后去掉了中间变量b,直接定位到原DataFrame的指定位置修改,完全规避了切片副本问题,不会再触发警告,逻辑和你原来的实现完全一致,计算结果也相同。
内容的提问来源于stack exchange,提问作者brosenheim
相关产品推荐
相关产品推荐

