【问题标题】:pandas perform interpolation over array and dataframe row without looppandas 在没有循环的情况下对数组和数据帧行执行插值
【发布时间】:2022-01-24 18:32:52
【问题描述】:

我有一个相当大的数据框,我想要

  1. 按行搜索包含值的区间
  2. 在点 1 找到的两个元素和另一个数组中的两个元素之间执行线性插值
  3. 使用插值向数据框添加一列

我所做的涉及一个 for 循环,即:

给定一个数据框样本Fak

     beta0     beta1     beta2     beta3     beta4     beta5     beta6     beta7     beta8     beta9    beta10
0    0.008665  0.061391  0.159690  0.223275  0.232535  0.251266  0.279847  0.465671  0.672253  0.914753 1.0
1    0.009121  0.064322  0.166623  0.232418  0.241945  0.261106  0.290169  0.477621  0.682283  0.916384 1.0
2    0.009491  0.066689  0.172210  0.239776  0.249516  0.269020  0.298463  0.487108  0.690031  0.917638 1.0
3    0.009733  0.068232  0.175837  0.244542  0.254418  0.274140  0.303820  0.493102  0.694703  0.918304 1.0
4    0.009860  0.069027  0.177687  0.246963  0.256906  0.276734  0.306523  0.495985  0.696696  0.918511 1.0

我有一个数组psi

[-12.97, -11.97, -10.97, -9.97, -8.97, -7.97, -6.97, -5.97, -4.97, -3.97, -2.97, -1.97]

我在Fak中定义了我要搜索的值,即intF = 0.16

我使用以下循环计算新数据帧

dxlist = []
for i,Faki in Fak.iterrows():
    # interpolation boundaries ID
    if intF == 0.0:
        ip1 = 1
    elif intF == 1.0:
        ip1 = -1
    else:
        ip1 = np.where(Faki>int(intF)/100)[0][0]
    im1 = ip1-1
    # coefficients
    dfak = Faki[ip1] - Faki[im1]
    dpsi = psi[ip1] - psi[im1]
    m = dfak/dpsi
    q = Faki[im1]-m*psi[im1]
    # calculate
    intPsi = (int(intF)/100-q)/m
    intDi  = 2**intPsi
    dxlist.append(intDi)
dfout['newcolumn'] = dxlist

这行得通,但速度很慢。

我缺少的是如何逐行计算线性插值并使用外部数组上的索引。

【问题讨论】:

  • 你试过用 .apply 方法吗?
  • .iterrows 方法是一种非常低效的处理数据框的方法,尤其是当它变得越来越大时。有一些更好的建议here
  • @JoaoDonasolo 当然可以,但是如何?我的意思是我需要在每一行上找到一个索引,将它应用于一个数组,然后计算一个新值以附加到一个新列。如何将这三个操作包装在一个应用命令中?
  • @DerekO 当然,我会看看那个,但我认为在这种情况下矢量化不是一个选项。

标签: python pandas dataframe interpolation


【解决方案1】:

显然我找到了一个矢量化的解决方案:

psidf = Fak.copy()
psidf.loc[Fak.index] = psi
Fakp1 = Fak[Fak.ge(intF/100)].fillna(method='bfill',axis=1).iloc[:,0]
Fakm1 = Fak[Fak.le(intF/100)].fillna(method='ffill',axis=1).iloc[:,-1]
psip1 = psidf[Fak.ge(intF/100)].fillna(method='bfill',axis=1).iloc[:,0]
psim1 = psidf[Fak.le(intF/100)].fillna(method='ffill',axis=1).iloc[:,-1]
m     = (Fakp1-Fakm1)/(psip1-psim1)
q     = Fakm1-m*psim1
intDi_series = 2**((intF/100-q)/m)
intDi['d'+str(int(intF))+nsfx] = intDi_series

关键是生成一个以数组为行的数据库,与Fak的形状相同(在上面代码的前两行中完成)。

然后,我使用 pandas 数据帧的 gele 方法从每个数据帧中分离出我需要的列,并在新生成的数据帧中使用索引

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2019-11-29
    • 2021-05-13
    • 1970-01-01
    • 2019-12-26
    • 2020-09-05
    • 1970-01-01
    • 2018-04-11
    相关资源
    最近更新 更多