如何编写返回内插值的函数(Pandas DataFrame)?
问题描述
我有一个作为 pandas 数据帧导入的XLS文件。它有NaN值;我如何设置一个函数,用相邻值之间的插值法替换NaN?我不能使用pd.DataFrame.interpolate或任何现有的内插函数,因为我应该创建自己的函数。
这是我所拥有的,但我认为这是非常错误的。抱歉,对Python来说还很陌生:(
import pandas as pd
file = pd.read_excel("xls file")
def interpolate(x):
for i in range(len(x)):
if x.iloc[i, -1].isnull():
x.iloc[i,-1] = (((x.iloc[i-1, -1]) + (x.iloc[i+1, -1]))/2)
else:
x.iloc[i,-1] = x.iloc[i, -1]
interpolate(file)
例如,数据帧最初看起来如下所示:
0 1.04
1 0.99
2 NaN
3 1.05
4 1.05
我希望它返回:
0 1.04
1 0.99
2 1.02
3 1.05
4 1.05
为此,假设没有连续的NaN条目
解决方案
此解决方案使用默认参数重新创建pd.Series.interpolate
的行为。这不是一个适合初学者的解决方案,如果你的问题是家庭作业,我很好奇你的教授会期待什么。
我使用的数据帧具有前导、尾随和连续的nan
值。我添加了一个带有插值值的列,以与我的解决方案进行比较。需要具有默认排序范围索引的Series
。
import pandas as pd
import numpy as np
np.random.seed(11)
a = np.where(np.random.rand(20) > .5, np.random.uniform(0,10, 20), np.nan)
df = pd.DataFrame({
'x': a
})
df['x_interp'] = df.x.interpolate()
df
输出
x x_interp
0 NaN NaN
1 NaN NaN
2 NaN NaN
3 3.187988 3.187988
4 NaN 2.661738
5 NaN 2.135487
6 NaN 1.609237
7 NaN 1.082987
8 0.556737 0.556737
9 4.797973 4.797973
10 4.016765 4.016765
11 NaN 5.597628
12 7.178492 7.178492
13 6.020641 6.020641
14 NaN 7.755832
15 9.491024 9.491024
16 NaN 9.491024
17 NaN 9.491024
18 NaN 9.491024
19 NaN 9.491024
方法是使用nan
和周围的值查找切片。然后在周围的值之间用线性步长填充这些切片。ffill
参数控制尾部nan
是否将用最后一个可用值填充。
def interp(ser, ffill=True):
ser = ser[df.x.notna().idxmax():].copy()
start = ser.notna() & ser.shift(-1, fill_value=0).isna()
end = ser.notna() & ser.shift(1, fill_value=0).isna()
for x,y in zip(ser.index[start],ser.index[end]):
step = (ser.loc[y] - ser.loc[x])/(y - x)
ser.loc[x:y] = [ser.loc[x] + i * step for i in range(y-x)] + [ser.loc[y]]
if ffill:
ser = ser.ffill()
return ser
df['x_new_interp'] = interp(df.x, False)
df['x_new_interp_ffill'] = interp(df.x)
df
输出
x x_interp x_new_interp x_new_interp_ffill
0 NaN NaN NaN NaN
1 NaN NaN NaN NaN
2 NaN NaN NaN NaN
3 3.187988 3.187988 3.187988 3.187988
4 NaN 2.661738 2.661738 2.661738
5 NaN 2.135487 2.135487 2.135487
6 NaN 1.609237 1.609237 1.609237
7 NaN 1.082987 1.082987 1.082987
8 0.556737 0.556737 0.556737 0.556737
9 4.797973 4.797973 4.797973 4.797973
10 4.016765 4.016765 4.016765 4.016765
11 NaN 5.597628 5.597628 5.597628
12 7.178492 7.178492 7.178492 7.178492
13 6.020641 6.020641 6.020641 6.020641
14 NaN 7.755832 7.755832 7.755832
15 9.491024 9.491024 9.491024 9.491024
16 NaN 9.491024 NaN 9.491024
17 NaN 9.491024 NaN 9.491024
18 NaN 9.491024 NaN 9.491024
19 NaN 9.491024 NaN 9.491024
相关文章