繁体   English   中英

Python:使用列表推导生成对称数组

[英]Python: Generating a symmetric array with list comprehension

我试图生成矩阵A == [f(i,j) for i,j in range(0,n)] 矩阵是对称的(f(i,j) == f(j,i))并且对角元素是零(f(i,i) == 0)

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

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


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

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

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

首先创建矩阵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

如果我理解正确,就不需要额外的存储空间。 在练习潜艇的列表理解中调用g

如果希望函数仅在i <j时执行,则可以使用lru_cache(@lru_cache)将函数的结果保存在缓存中,并在i> j时直接使用它而无需重新计算。

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]

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM