【问题标题】:Fill a matrix in parallel并行填充矩阵
【发布时间】:2016-10-28 00:22:19
【问题描述】:

我有一个关于如何并行填充矩阵的问题。我正在尝试在 Python 中逐行进行。但是并行执行的时间比顺序处理时间最差。我怎样才能有效地做到这一点?注意:我需要知道索引的值(ij)。

顺序

def something(pos, size):
    global matrix

    numpy.zeros(shape=(size, size))

    for i in xrange(size):
        matrix[i][i] = 0.0

        i_lat = pos[i]['lat']
        i_lon = pos[i]['lon']

        for j in xrange(i + 1, size):
             matrix[j][i] = matrix[i][j] = _matrix_update(pos, i_lat, i_lon, i, j)

def _matrix_update(pos, lat, lon, u, v):
    return 0.0 if u == v else euclidean_distance((lat, lon), (pos[v]['lat'], pos[v]['lon']))

平行

def something(pos, size):
    global matrix

    numpy.zeros(shape=(size, size))

    for i in xrange(size):
        matrix[i][i] = 0.0

        i_lat = pos[i]['lat']
        i_lon = pos[i]['lon']

        Parallel(n_jobs=mp.cpu_count())(delayed(_matrix_update)(pos, i_lat, i_lon, i, j) for j in xrange(i, size))

def _matrix_update(pos, lat, lon, u, v):
    global matrix
    matrix[u][v] = matrix[v][u] = (0.0 if u == v else euclidean_distance((lat, lon), (pos[v]['lat'], pos[v]['lon'])))

【问题讨论】:

  • 我认为它可以以矢量化的方式完成,无需循环。您能否使用示例输入矩阵(5 行就足够了)更新您的问题,简要说明您要如何处理此数据和所需的结果矩阵?
  • 你可能还想检查those vectorized函数
  • 在这种情况下,我不能使用 Numpy,因为 euclidean_distance 函数是适合这种情况的方法,并且没有框架按照我的需要实现它。

标签: python loops numpy parallel-processing


【解决方案1】:

您的代码提出了一大堆问题,太多问题无法放入 cmets。

def something(pos, size):
    global matrix      

matrix 是什么?为什么global?由于您正在对其进行变异,因此即使它是在此函数之外定义的,也不需要全局。但我更愿意看到它作为参数传入和传出。

    numpy.zeros(shape=(size, size))

这句话的意义何在?你为什么不将结果分配给任何东西?应该是matrix = np.zeros(shape...)?在这种情况下,matrix 是在函数中创建的,并且应该在 return matrix 语句中,而不是全局语句中。

    for i in xrange(size):
        matrix[i][i] = 0.0

如果matrix 是二维数组,则使用matrix[i,i] = 0 对其进行索引。但是如果它是用zeros 表达式创建的,这个对角线已经是0了。

        i_lat = pos[i]['lat']
        i_lon = pos[i]['lon']

pos 是什么?语法表明它是一个结构化数组,即第 i 个记录的“纬度”字段。不是字典列表吗?

        for j in xrange(i + 1, size):
             matrix[j][i] = matrix[i][j] = _matrix_update(pos, i_lat, i_lon, i, j)

所以你在这里设置对称值。当迭代完成时,这是一个很好的方法。是np.tri... 处理上下三角数组的函数。

def _matrix_update(pos, lat, lon, u, v):
    return 0.0 if u == v else euclidean_distance((lat, lon), (pos[v]['lat'], pos[v]['lon']))

鉴于您对 i 和 j 的迭代方式,u==v 永远不会发生,因此可以将更新简化为

j_lat, j_lon = pos[j]['lat'], pos[j]['lon']
matrix[j,i] = matrix[i,j] = euclidean_distance((i_lat, i_lon), (j_lat, j_lon))

我不希望这些更改会加快计算速度,但它们应该会让计算更加清晰。

这是什么Parallel?您需要提供有关您正在使用的模块或包的更多信息。这是试图使用多个核心的东西吗?是否已知可与 matrix 一起使用(它是什么)?

euclidian_distance 函数是什么?从其他地方进口的?

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2020-04-19
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多