簡體   English   中英

Python中的對角矩陣指數

[英]Diagonal Matrix Exponential in Python

我正在編寫一個考慮速度的數值算法。 我在scipy / numpy(scipy.linalg.expm2,scipy.linalg.expm)中遇到了兩個矩陣指數函數。 但是我有一個矩陣,我知道它是預先對角的。 這些scipy函數是否在運行之前檢查矩陣是否是對角線? 顯然,對於對角矩陣,求冪算法可以快得多,我只是想確保它們正在做一些聰明的東西 - 如果它們不是,那么有一種簡單的方法嗎?

如果矩陣是對角線,則可以通過對主對角線上的每個條目取冪來獲得其指數,因此您可以通過以下方式計算:

np.diag(np.exp(np.diag(a)))

如果你知道A是對角線而你想要k次冪:

def dpow(a, k):
    return np.diag(np.diag(a) ** k)

檢查矩陣是否是對角線:

def isdiag(a):
    return np.all(a == np.diag(np.diag(a)))

所以:

def pow(a, k):
    if isdiag(a):
        return dpow(a, k)
    else:
        return np.asmatrix(a) ** k

類似地,對於指數(你可以通過擴展一套pow來數學獲得),你可以做到:

def dexp(a, k):
    return np.diag(np.exp(np.diag(a)))

def exp(a, k):
    if isdiag(a):
        return dexp(a, k)
    else:
        #use scipy.linalg.expm2 or whatever

我開發了一個工具,可以幫助更快地像HYRY一樣做,但是通過就地做到這一點:

def diagonal(array):
    """ Return a **view** of the diagonal elements of 'array' """
    from numpy.lib.stride_tricks import as_strided
    return as_strided(array,shape=(min(array.shape),),strides=(sum(array.strides),))

# generate a random diagonal array
d  = np.diag(np.random.random(4000))

# in-place exponent of the diagonal elements
ddiag = diagonal(d)
ddiag[:] = np.exp(ddiag)

# timeit comparison with HYRY's method
%timeit -n10 np.diag(np.exp(np.diag(d)))   
    # out> 10 loops, best of 3: 52.1 ms per loop
%timeit -n10 ddiag = diagonal(d); ddiag[:] = np.exp(ddiag)
    # out> 10 loops, best of 3: 108 µs per loop

現在,

  • HYRY的方法是對角線長度的二次方(可能是因為新的數組內存分配),所以如果你的矩陣的維度很小,差異可能不會那么大。

  • 你需要在原地計算中做好

  • 最后,非對角元素為0,因此它們的指數應為1,不應該嗎? 在我們的方法中,非對角線都是0。

對於最后一部分,如果您希望所有非對角元素為1,那么您可以:

d2 = np.ones_like(d); 
diagonal(d2)[:] = np.exp(np.diag(d))

print (d2==np.exp(d)).all()  # True

但這對於數組大小是線性的,因此對角線長度是二次方的。 對於4000x4000陣列,時間給出~90ms,對於2000x2000,給出22.3ms。

最后,你也可以在原地進行加速:

diag = np.diag(d)
d[:]=1
diagonal(d)[:] = np.exp(diag)

Timeit為4000 ^ 2陣列提供66.1ms,為2000 ^ 2提供16.8ms

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM