【问题标题】:Calculating new entries in array based on entries from another array in python根据python中另一个数组的条目计算数组中的新条目
【发布时间】:2015-03-10 16:11:58
【问题描述】:

我有一个问题,基于如何“调用”数组中的特定单元格,同时遍历另一个数组。 假设有一个数组a:

    a = [[a1 a2 a3],[b1 b2 b3]]

还有一个数组 b:

    b = [[c1 c2] , [d1 d2]]

现在,我想使用数组 a 中的信息重新计算数组 b 中的值。具体来说,数组 b 的每个值都必须通过乘以数组 a 中给定的边界之间的高斯函数的积分来重新计算。但是为了简单起见,让我们忘记积分,并假设一个简单的计算是必要的:

    c1 = c1 * (a2-a1) ; c2 = c2 * (a3 - a2) and so on,

使用索引它可能看起来像:

    b[i,j] = b[i,j] * (a[i, j+1] - a[i,j])

谁能告诉我如何解决这个问题? 非常感谢和最好的问候, 马克

【问题讨论】:

  • 你的意思是c[i,j] = b[i,j] * (a[i, j+1] - a[i,j])
  • a 中的元素a1a2a3a[0][0]a[0][1]a[0][2],以及元素@9876543@33@、@9876543433和a 中的b3a[1][0]a[1][1]a[1][2]。令人困惑的是,a 数组中有名为 b 的元素。无论如何,鉴于此,您应该能够弄清楚 b 数组中元素的索引是什么。

标签: python arrays loops


【解决方案1】:

您可以在嵌套列表推导中使用 zip 函数:

>>> [[k*(v[1]-v[0]) for k,v in zip(v,zip(s,s[1:]))] for s,v in zip(a,b)]

zip(s,s[1:]) 会给你想要的元素对,例如:

>>> s =[4, 5, 6]
>>> zip(s,s[1:])
[(4, 5), (5, 6)]

演示:

>>> b =[[7, 8], [6, 0]]
>>> a = [[1,5,3],[4 ,0 ,6]]
>>> [[k*(v[1]-v[0]) for k,v in zip(v,zip(s,s[1:]))] for s,v in zip(a,b)]
[[28, -16], [-24, 0]]

【讨论】:

  • 我想他想要[[v[idx]*(j-i) for idx, (i,j) in enumerate(zip(s,s[1:]))] for s,v in zip(a,b)]
  • @Alex 是的,在您提醒的同时编辑! ;)
  • 谢谢你们!我试过 X = [[k*(scipy.integrate.quad(f, v[1], v[0])) for k,v in zip(v,zip(s,s[1:]))] for s,v 在 zip(a,b)] 中。我确定它有效,但我需要对函数 f 进行特殊处理。我定义了 f = lambda x : 1/np.sqrt(2*pi)*gs_wdth) * np.exp(-(x-mean)**2/(2*gs_wdth**2)) 高斯宽度是上面的每个计算都是一样的。数组 a/b 中每条“线”的“平均”值都会发生变化。对于 b = [[7,8],...]; a = [[1,5,3],...] gs_wdth 例如2,对于 b = [...,[6,0]] ; a = [...,[4,0,6]] gs_wdth 例如4. gs_wdth 列在一个数组中,例如wdt=[2,4]。可以加入吗?
【解决方案2】:

你也可以用 numpy 干净利落地做到这一点:

import numpy as np
a, b = np.array(a), np.array(b)
np.diff(a) * b

【讨论】:

    【解决方案3】:

    首先,我会将您的表拆分为下限表和上限表,以使用对齐的表并提高可读性:

    lowerBounds = a[...,:-1]
    upperBounds = a[...,1:]
    

    定义你提供的高斯函数:

    def f(x, gs_wdth = 1., mean=0.):
        return 1./numpy.sqrt(2*numpy.pi)*gs_wdth * numpy.exp(-(x-mean)**2/(2*gs_wdth**2))
    

    然后,使用nditer(参见Iterating Over Arrays)高效地遍历数组:

    it = numpy.nditer([b, lowerBounds, upperBounds],
                       op_flags=[['readwrite'], ['readonly'], ['readonly']])
    for _b, _lb, _ub in it:
        multiplier = scipy.integrate.quad(f, _lb, _ub)[0]
        _b[...] *= multiplier
    print b
    

    这可以完成您帖子中所需的工作,并且应该具有计算效率。请注意,b 在修改后的“就地”中:原始值丢失但计算过程中没有内存溢出。

    【讨论】:

    • 我尝试了您的版本,使用以下代码:multiplier = scipy.integrate.quad(f, _lb, _ub) 但不幸的是,他遇到了问题并做出以下标注:ValueError:真相具有多个元素的数组的值不明确。使用 a.any() 或 a.all() 我必须在哪里填写 any() 或 all() 或者甚至可以解决问题?
    • 问题是 scipy.integrate.quad 没有矢量化,并且需要浮点参数作为下限和上限。解决方案是通过删除 external_loop 标志一次提供一个迭代数组的元素。我改变我的答案来反映这一点。不过,这应该会降低计算效率。
    猜你喜欢
    • 1970-01-01
    • 2011-04-05
    • 1970-01-01
    • 2018-12-17
    • 2022-08-17
    • 2021-07-07
    • 2017-11-02
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多