2016-04-25 18 views
2

numpy.linalg.matrix_rank()を使用して奇妙な問題が発生しています。
私は3つの列と> 100行を持つ行列Aを持っています。 Aは0と1で構成されます。 numpy.linalg.matrix_rank(A)を使用すると、私はanswer=3を取得しましたが、これは正しいです。
しかし、Aと同じ長さの新しい列を追加すると(今は4つの列があります)、numpy.linalg.matrix_rank(A)を使用すると意味をなさないanswer=1が得られます。新しい列の数値は千単位です。すべてのデータ型はfloat32です。numpy行列ランク不正確結果

どこに問題があるか知っていますか?ありがとう!

ランダムに生成された例です。これは、40×3アレイA.

array([[ 0., 0., 1.], [ 0., 0., 1.], [ 0., 0., 1.], [ 0., 0., 1.], [ 0., 0., 1.], [ 0., 0., 1.], [ 0., 0., 1.], [ 0., 0., 1.], [ 0., 0., 1.], [ 0., 0., 1.], [ 0., 0., 1.], [ 0., 0., 1.], [ 0., 0., 1.], [ 0., 0., 1.], [ 0., 0., 1.], [ 0., 0., 1.], [ 0., 0., 1.], [ 0., 0., 1.], [ 0., 0., 1.], [ 0., 0., 1.], [ 0., 0., 1.], [ 0., 0., 1.], [ 0., 0., 1.], [ 0., 0., 1.], [ 0., 0., 1.], [ 0., 0., 1.], [ 0., 0., 1.], [ 0., 0., 1.], [ 0., 0., 1.], [ 0., 0., 1.], [ 0., 0., 1.], [ 0., 0., 1.], [ 0., 0., 1.], [ 0., 0., 1.], [ 0., 0., 1.], [ 0., 0., 1.], [ 0., 0., 1.], [ 0., 0., 1.], [ 1., 0., 1.], [ 1., 1., 1.]], dtype=float32)

numpy.linalg.matrix_rank(A)今3

であり、Iは第4列を追加し、Aは、次のようになる:

array([[ 6.42096562e+04, 0.00000000e+00, 0.00000000e+00, 
     1.00000000e+00], 
    [ 2.15370996e+04, 0.00000000e+00, 0.00000000e+00, 
     1.00000000e+00], 
    [ 1.28050068e+04, 0.00000000e+00, 0.00000000e+00, 
     1.00000000e+00], 
    [ 3.20350176e+04, 0.00000000e+00, 0.00000000e+00, 
     1.00000000e+00], 
    [ 4.26681055e+04, 0.00000000e+00, 0.00000000e+00, 
     1.00000000e+00], 
    [ 1.55057520e+04, 0.00000000e+00, 0.00000000e+00, 
     1.00000000e+00], 
    [ 6.82897266e+04, 0.00000000e+00, 0.00000000e+00, 
     1.00000000e+00], 
    [ 5.29479727e+04, 0.00000000e+00, 0.00000000e+00, 
     1.00000000e+00], 
    [ 2.54858457e+04, 0.00000000e+00, 0.00000000e+00, 
     1.00000000e+00], 
    [ 9.82017109e+04, 0.00000000e+00, 0.00000000e+00, 
     1.00000000e+00], 
    [ 4.03392627e+03, 0.00000000e+00, 0.00000000e+00, 
     1.00000000e+00], 
    [ 2.24184062e+04, 0.00000000e+00, 0.00000000e+00, 
     1.00000000e+00], 
    [ 6.90389688e+04, 0.00000000e+00, 0.00000000e+00, 
     1.00000000e+00], 
    [ 2.75718145e+04, 0.00000000e+00, 0.00000000e+00, 
     1.00000000e+00], 
    [ 6.67467109e+04, 0.00000000e+00, 0.00000000e+00, 
     1.00000000e+00], 
    [ 4.78061758e+04, 0.00000000e+00, 0.00000000e+00, 
     1.00000000e+00], 
    [ 1.52730410e+04, 0.00000000e+00, 0.00000000e+00, 
     1.00000000e+00], 
    [ 9.13073359e+04, 0.00000000e+00, 0.00000000e+00, 
     1.00000000e+00], 
    [ 1.51932471e+04, 0.00000000e+00, 0.00000000e+00, 
     1.00000000e+00], 
    [ 9.27319297e+04, 0.00000000e+00, 0.00000000e+00, 
     1.00000000e+00], 
    [ 7.41743359e+04, 0.00000000e+00, 0.00000000e+00, 
     1.00000000e+00], 
    [ 7.98595469e+04, 0.00000000e+00, 0.00000000e+00, 
     1.00000000e+00], 
    [ 3.40574414e+04, 0.00000000e+00, 0.00000000e+00, 
     1.00000000e+00], 
    [ 3.12823730e+04, 0.00000000e+00, 0.00000000e+00, 
     1.00000000e+00], 
    [ 5.66580273e+04, 0.00000000e+00, 0.00000000e+00, 
     1.00000000e+00], 
    [ 4.53152070e+04, 0.00000000e+00, 0.00000000e+00, 
     1.00000000e+00], 
    [ 9.84440938e+04, 0.00000000e+00, 0.00000000e+00, 
     1.00000000e+00], 
    [ 7.13604375e+04, 0.00000000e+00, 0.00000000e+00, 
     1.00000000e+00], 
    [ 3.59290312e+04, 0.00000000e+00, 0.00000000e+00, 
     1.00000000e+00], 
    [ 8.91415820e+03, 0.00000000e+00, 0.00000000e+00, 
     1.00000000e+00], 
    [ 5.73751992e+04, 0.00000000e+00, 0.00000000e+00, 
     1.00000000e+00], 
    [ 3.96208867e+04, 0.00000000e+00, 0.00000000e+00, 
     1.00000000e+00], 
    [ 2.06492324e+04, 0.00000000e+00, 0.00000000e+00, 
     1.00000000e+00], 
    [ 1.50155918e+04, 0.00000000e+00, 0.00000000e+00, 
     1.00000000e+00], 
    [ 6.47758789e+02, 0.00000000e+00, 0.00000000e+00, 
     1.00000000e+00], 
    [ 9.27601094e+04, 0.00000000e+00, 0.00000000e+00, 
     1.00000000e+00], 
    [ 9.77911621e+03, 0.00000000e+00, 0.00000000e+00, 
     1.00000000e+00], 
    [ 5.01128320e+04, 0.00000000e+00, 0.00000000e+00, 
     1.00000000e+00], 
    [ 7.21259922e+04, 1.00000000e+00, 0.00000000e+00, 
     1.00000000e+00], 
    [ 6.10147461e+03, 1.00000000e+00, 1.00000000e+00, 
     1.00000000e+00]], dtype=float32) 

numpy.linalg.matrix_rank(A)は2です。これは可能でしょうか?

+4

あなたは、再現性の例を提供することはできますか? –

+3

こんにちは... StackOverflowへようこそ。質問をするときは、問題を再現できるようにする必要があります。あなたの質問には、目的、現在の結果、エラー、これまでに試したことを含める必要があります。コードと、可能であれば、再現するデータや何か正確なエラーを共有してください。ありがとう。 – Pouria

+1

3つの列と追加する列(少なくとも上位10の値)を入力して表示できますか? 4列目の最大値は? –

答えて

5

「...意味をなさない」実際には、matrix_rankと推定される場合は、ランクで意味があります。 matrix_rankは、単に0でない行列のsingular valuesの数を数えます。特異値は、最大特異値に対して小さい場合は0とみなされます。数字が「千単位」の4番目の列を追加すると、大きな特異値が追加されます。 3つの元の特異値は、新しい大きな値と比較して小さいので、0とみなされ、ランクには数えられません。

例を示します。 Aは0と1の配列です。 BAに100000を含む列を追加することによって作成される:

In [217]: np.random.seed(123) 

In [218]: A = np.random.randint(0, 2, size=(100, 3)).astype(np.float32) 

In [219]: B = np.hstack((A, 100000*np.ones((A.shape[0], 1)))).astype(np.float32) 

予想されたように、Aランク3を有する:ここ

In [220]: np.linalg.matrix_rank(A) 
Out[220]: 3 

Aの特異値である。

In [221]: np.linalg.svd(A)[1] 
Out[221]: array([ 9.98757744, 5.41796255, 4.88814735], dtype=float32) 

同様あなたの例、Bはランク1を持っています:

In [222]: np.linalg.matrix_rank(B) 
Out[222]: 1 

Bは、他の3つの値よりもはるかに大きい1つの特異値を持つことがわかります。

In [223]: np.linalg.svd(B)[1] 
Out[223]: 
array([ 1.00000000e+06, 5.45980692e+00, 4.90207911e+00, 
     4.59457588e+00], dtype=float32) 

matrix_rankアカウントにデータ型を取ること:大きさの差はmatrix_rankが小さい特異値がほぼ0であることを考慮することで十分です。 Bは、64ビット浮動小数点に変換されている場合は、matrix_rankによって計算されたランクは4です:

In [226]: np.linalg.matrix_rank(B.astype(np.float64)) 
Out[226]: 4 
+0

ありがとう!意味あり。私はこの例を質問に移しました。 –

関連する問題