2016-07-17 84 views

Antwort

5

Dies ist die rvs Methode aus den https://github.com/scipy/scipy/pull/5622/files gezogen, mit minimalen Veränderungen - gerade genug, um als Stand-alone numpy Funktion auszuführen.

import numpy as np  

def rvs(dim=3): 
    random_state = np.random 
    H = np.eye(dim) 
    D = np.ones((dim,)) 
    for n in range(1, dim): 
     x = random_state.normal(size=(dim-n+1,)) 
     D[n-1] = np.sign(x[0]) 
     x[0] -= D[n-1]*np.sqrt((x*x).sum()) 
     # Householder transformation 
     Hx = (np.eye(dim-n+1) - 2.*np.outer(x, x)/(x*x).sum()) 
     mat = np.eye(dim) 
     mat[n-1:, n-1:] = Hx 
     H = np.dot(H, mat) 
     # Fix the last sign such that the determinant is 1 
    D[-1] = (-1)**(1-(dim % 2))*D.prod() 
    # Equivalent to np.dot(np.diag(D), H) but faster, apparently 
    H = (D*H.T).T 
    return H 

Sie paßt Warren-Test, https://stackoverflow.com/a/38426572/901925

13

Version 0.18 von scipy hat scipy.stats.ortho_group und scipy.stats.special_ortho_group. Die Pull-Anforderung, wo es aufgenommen wurde, ist https://github.com/scipy/scipy/pull/5622

Zum Beispiel

In [24]: from scipy.stats import ortho_group # Requires version 0.18 of scipy 

In [25]: m = ortho_group.rvs(dim=3) 

In [26]: m 
Out[26]: 
array([[-0.23939017, 0.58743526, -0.77305379], 
     [ 0.81921268, -0.30515101, -0.48556508], 
     [-0.52113619, -0.74953498, -0.40818426]]) 

In [27]: np.set_printoptions(suppress=True) 

In [28]: m.dot(m.T) 
Out[28]: 
array([[ 1., 0., -0.], 
     [ 0., 1., 0.], 
     [-0., 0., 1.]]) 
+0

Vielen Dank für Ihre Antwort. Ich habe bemerkt, dass die gegebenen Antworten alle für quadratische Matrizen sind. Kann ich diese Methode noch verwenden, um eine d x k Matrix zu erhalten, wobei k Dacion

7

Sie können Q, eine zufällige n x n orthogonale Matrix erhalten (gleichmäßig den Verteiler von n x n orthogonalen Matrizen verteilt), indem eine QR Faktorisierung einer n x n Matrix mit den Elementen der Durchführung i.i.d. Gaußsche Zufallsvariablen des Mittelwerts 0 und der Varianz 1. Hier ein Beispiel:

import numpy as np 
from scipy.linalg import qr 

n = 3 
H = np.random.randn(n, n) 
Q, R = qr(H) 

print (Q.dot(Q.T)) 
[[ 1.00000000e+00 -2.77555756e-17 2.49800181e-16] 
[ -2.77555756e-17 1.00000000e+00 -1.38777878e-17] 
[ 2.49800181e-16 -1.38777878e-17 1.00000000e+00]] 
0

, wenn Sie eine keine quadratische Matrix wollen mit orthonormal Spaltenvektoren Sie ein Quadrat ein mit einem der genannten Verfahren schaffen könnte und einige Spalten fallen.