类中__init__调用的方法与外部调用同方法输出不一致问题
问题分析与解决
核心问题
你代码里的inst.levels返回整个DataFrame,是因为在__init__方法中调用pivot_points时没有使用实例调用(self.pivot_points),导致Python没有执行类内部的实例方法,反而调用了全局作用域中同名的、返回DataFrame的函数(你之前在类外定义过的版本)。
修正方案
方案1:正确调用类内部的实例方法
修改__init__中的调用方式,通过self调用类的pivot_points方法:
class Backtest: def __init__(self, ticker, df): self.ticker = ticker self.df = df # 用self调用类内部的pivot_points方法 self.levels = self.pivot_points(self.df) def pivot_points(self, df, period=30): highs = scipy.signal.argrelmax(df.High.values, order=period) lows = scipy.signal.argrelmin(df.Low.values, order=period) return list(df.High[highs[0]]) + list(df.Low[lows[0]])
方案2:优化封装(更推荐)
既然df已经是实例属性self.df,可以让pivot_points方法直接使用实例属性,无需传参:
import pandas as pd import numpy as np import scipy gold = pd.DataFrame({'Open':[i for i in range(100)],'Close':[i for i in range(100)],'High':[i for i in range(100)],'Low':[i for i in range(100)]}) class Backtest: def __init__(self, ticker, df): self.ticker = ticker self.df = df # 无需传df,直接调用方法 self.levels = self.pivot_points() def pivot_points(self, period=30): # 直接使用实例属性self.df highs = scipy.signal.argrelmax(self.df.High.values, order=period) lows = scipy.signal.argrelmin(self.df.Low.values, order=period) return list(self.df.High[highs[0]]) + list(self.df.Low[lows[0]]) inst = Backtest('gold', gold) print(inst.levels) # 现在会返回预期的整数列表
关键原理
类中的实例方法必须通过实例对象(self)来调用,否则Python会优先在全局命名空间查找同名函数,而非执行类内部的方法。你之前在类外调用能得到正确结果,是因为直接调用了全局的pivot_points函数,但类内部的方法没有被正确触发。
内容的提问来源于stack exchange,提问作者Rey Fit
相关产品推荐
相关产品推荐

