【问题标题】:Python: Generating a symmetric array with list comprehensionPython:使用列表理解生成对称数组
【发布时间】:2017-03-05 08:23:57
【问题描述】:

我正在尝试生成矩阵A == [f(i,j) for i,j in range(0,n)]。矩阵是对称的(f(i,j) == f(j,i)),对角元素为零(f(i,i) == 0)

问题:是否可以生成一个列表推导式来生成这个矩阵但只为i < j 调用函数f(i,j)

不是我的问题:以其他方式生成对称矩阵。


可能的解决方案:通过辅助函数g调用f,将f的值保存在额外的存储中或返回存储的值。

是否可以解决避免额外存储的问题? 我不确定这个额外的障碍是否意味着对列表理解本身的引用(我读到的 Python 中不存在)是必要的,希望我错过了一些其他技巧。

【问题讨论】:

标签: python arrays list-comprehension


【解决方案1】:

假设你真的需要完整的矩阵,尽管它是对称的,你可以这样做。

首先创建矩阵A。 (我知道,这意味着您不是在列表推导中生成它。)在这里,我定义了一个“虚拟”函数 f 并假设 n 的值为 3。

>>> n=3
>>> subs=((i,j) for i in range(n) for j in range(3) if i<=j)
>>> for i,j in subs:
...     i,j
...     
(0, 0)
(0, 1)
(0, 2)
(1, 1)
(1, 2)
(2, 2)
>>> def f(i,j):
...     return
... 
>>> def g(i,j):
...     if i==j:
...         A[i,i] = 0
...     else:
...         val=f(i,j)
...         A[i,j]=val
...         A[j,i]=val

如果我的理解正确,则不需要额外的存储空间。在执行 subs 的列表理解中调用 g

【讨论】:

  • 这算是一个解决方案。
【解决方案2】:

如果希望函数只在ij时直接使用,无需重新计算。

from typing import Any
from functools import lru_cache

@lru_cache()
def f(i: int, j: int) -> Any:
    return i * (-j)

n = 5
m = [f(i, j) if i < j else f(j, i) if i > j else 0 for i in range(n) for j in range(n)]

for i in range(0, n * n, n):
    print(m[i: i + n])

结果

[0, 0, 0, 0, 0]
[0, 0, -2, -3, -4]
[0, -2, 0, -6, -8]
[0, -3, -6, 0, -12]
[0, -4, -8, -12, 0]

【讨论】:

  • 酷。 lru_cache。不知道那个。
猜你喜欢
  • 2020-10-08
  • 1970-01-01
  • 2016-10-04
  • 2017-10-04
  • 2020-07-13
  • 2020-07-19
  • 1970-01-01
  • 1970-01-01
  • 2011-08-05
相关资源
最近更新 更多