にわかオタクによるにわか忘備録

にわかなオタクの試行錯誤を忘備録的にまとめているブログです.にわかなのでやってる事が全体的にお遊び感ある&所々誤りがあるのは否めませんが,生暖かい目で見ていただければと思います.

Numpy, Scipyの乱数・行列操作関連忘備録

研究でNumpy,Scipyを時々使うのだが,ボケ老人なので文法や関数を忘れてしまうことがある.いい機会なのでQ&A形式でまとめておきたいと思う.クソにわか野郎によるガバガバなメモなので信頼に値する記事を見たい人は公式のドキュメントか信頼できる方のブログを読んだ方がいいと思う.必要に応じて書き足すかも.

Q1.numpy.randomの乱数の種類忘れたんじゃが…

A.使いそうなものについては以下の通り.詳しいことは Random sampling (numpy.random) — NumPy v1.12 Manual を参照のこと.なおここでは全てimport numpy as npとしてnumpyを呼び出しているものとする.
  • np.random.rand(非負整数0, ..., 非負整数n)

乱数を区間[0,1)の一様分布に従って生成.出力は例えば以下の様になる.

>>> np.random.rand(2,3,4)
array([[[ 0.46601454,  0.3644631 ,  0.75478161,  0.43990995],
        [ 0.47596985,  0.99463364,  0.1834222 ,  0.83706576],
        [ 0.13573173,  0.46517434,  0.30557142,  0.40787683]],

       [[ 0.04593048,  0.59706683,  0.113075  ,  0.60624986],
        [ 0.96904384,  0.08106934,  0.70184092,  0.7407221 ],
        [ 0.73055882,  0.40888562,  0.62051385,  0.63620731]]])
  • np.random.randn(非負整数0, ..., 非負整数n)

乱数を標準正規分布に従って生成.出力は例えば以下の通り.

>>> np.random.randn(2,3,4)
array([[[ 0.83259091, -2.01459976,  0.6920033 , -0.36783596],
        [ 0.28946552, -0.58348612, -0.72452246, -0.13731635],
        [ 0.13756365,  1.54504672, -4.07175636,  0.26135016]],

       [[ 0.22061418, -2.28381171,  0.44716955,  0.13018847],
        [ 2.25960517,  1.21259798, -0.04677528,  0.15397896],
        [-0.60648996,  0.13623006,  0.69053053, -0.86730395]]])

平均mu標準偏差sigmaに従う乱数を生成したい時はsigma * np.random.randn(...)+mu

  • np.random.randint(low,high=None,サイズ,dtype=None)

区間[low,high)の一様分布に従ってランダムに整数を出力.dtypeでデータ型を変更することも出来る.

>>> np.random.randint(100) #下界値,サイズを指定しない場合は[0,low)の区間で乱数を1つだけ出力
37
>>> np.random.randint(10,100,3)
array([31, 51, 21])
  • np.random.random_integers(low,high=None,size=None)

区間[low,high]の離散一様分布に従ってランダムに整数を出力.randintとの違いは区間に上界値を含み,下界値を指定しない場合区間が[1,low]となり,かつデータ型を変えられない所.

  • np.random.random_sample(size=None)

区間[0.,1.)の連続一様分布に従いランダムに実数を出力.(b-a) * np.random.random_sample(n) + aとすれば区間を[a,b)に変更できる.

  • np.random.choice(list,size=None,replace=True,p=None)

リストの要素を離散一様分布に従いランダムにsize個だけ出力.pを書き換えれば確率を変更することも出来る.replaceがTrueの場合は復元抽出で,Falseの場合非復元抽出となる.

>>> np.random.choice(['a','b','c','d'],size=5,p=[0.4,0.3,0.2,0.1]) #確率分布はリストで渡す
array(['a', 'a', 'a', 'a', 'b'], 
      dtype='|S1')
>>> np.random.choice(['a','b','c','d'],size=5,replace=False,p=[0.4,0.3,0.2,0.1]) #当然っちゃ当然ではあるがlen(list)<sizeの時エラーを吐くので注意
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
  File "mtrand.pyx", line 1043, in mtrand.RandomState.choice (numpy/random/mtrand/mtrand.c:7776)
ValueError: Cannot take a larger sample than population when 'replace=False'

Q2.スパースな行列を扱ったり固有値問題解くためのいい方法何か無いの?

A.scipy.sparsesparse.linalg.eigsを使えばオッケー.詳細はSparse matrices (scipy.sparse) — SciPy v0.18.1 Reference Guidescipy.sparse.linalg.eigs — SciPy v0.19.0 Reference Guide を参照.

他のブログでも触れているとは思うが,行列がスカスカ(疎,スパース)な時はscipy.sparseを使えば計算が早くなるようだ.ついでにscipyでは固有値問題を解くためのパッケージもあるので簡単に紹介しておく.

  • sparse.lil_matrix(arg1,shape=None,dtype=None,copy=False)

スパースな行列を生成したりリストをスパース行列の形式に変換するための関数.これをやらないとscipyのスパース対応の議論ができない.具体的な使い方としては以下の通り.

from scipy import sparse
A = sparse.lil_matrix(5) #1×1のスパース行列が生成される(あまり嬉しくない)
B = sparse.lil_matrix([[1,0,0,...,0,0,1],...,[0,1,0,...,0,0,0]]) #2×2のリストを突っ込む(こっちの使い方の方が多そう)
C = sparse.lil_matrix((1000,10000)) #1000×10000のゼロ行列が出来る

ちなみにnp.arraylistとは異なりlen()を使うことが出来ないので,どうしてもリストの行の長さ等を取得したい場合一回a.todense()としてmatrixに直すなどする必要がある.

  • sparse.linalg.eigs(A, k=6, M=None, sigma=None, which='LM', v0=None, ncv=None, maxiter=None, tol=0, return_eigenvectors=True, Minv=None, OPinv=None, OPpart=None)

固有値問題A * x[i] = w[i] * x[i]を解き,k個の固有値固有ベクトルを出力する関数.詳しい使い方は公式のドキュメントもそうだが 固有値問題 - おっぱいそん! が非常に参考になる.とりあえずここでは使用例だけ書いておく.

>>> from scipy.sparse import linalg
>>> A = np.eye(13)
>>> vals, vecs = linalg.eigs(A, k=10) #ここで固有値,固有ベクトルを出力
>>> vals
array([ 1.+0.j,  1.+0.j,  1.+0.j,  1.+0.j,  1.+0.j,  1.+0.j,  1.+0.j,
        1.+0.j,  1.+0.j,  1.+0.j])
>>> vecs
array([[-0.41484689+0.j,  0.09212636+0.j,  0.13414715+0.j,  0.13446632+0.j,
        -0.38188830+0.j,  0.68967744+0.j, -0.17344782+0.j, -0.17612367+0.j,
         0.11405112+0.j,  0.13326663+0.j],
       [-0.17169938+0.j, -0.39948663+0.j, -0.50752858+0.j, -0.12445288+0.j,
        -0.13203875+0.j,  0.00406389+0.j,  0.48334069+0.j, -0.13880649+0.j,
         0.71734764+0.j, -0.14060811+0.j],
       [ 0.22865070+0.j, -0.56671006+0.j,  0.22221187+0.j,  0.47450244+0.j,
        -0.20815706+0.j, -0.16748905+0.j,  0.04002811+0.j, -0.06450019+0.j,
        -0.04261694+0.j,  0.07126702+0.j],
       [-0.29156719+0.j,  0.11505305+0.j, -0.09667384+0.j,  0.16509582+0.j,
         0.10322354+0.j,  0.28495352+0.j, -0.18647841+0.j,  0.00346095+0.j,
         0.06129625+0.j,  0.14166655+0.j],
       [-0.03916489+0.j, -0.32347004+0.j, -0.16732421+0.j, -0.07274700+0.j,
        -0.01334604+0.j, -0.07826815+0.j, -0.63449229+0.j,  0.67595659+0.j,
         0.21078900+0.j,  0.38548798+0.j],
       [ 0.01117841+0.j,  0.19268212+0.j,  0.03942106+0.j,  0.24304580+0.j,
        -0.03363494+0.j, -0.10162189+0.j, -0.20149455+0.j,  0.30008287+0.j,
         0.01645633+0.j, -0.77259180+0.j],
       [ 0.25256367+0.j, -0.11567280+0.j,  0.00601508+0.j, -0.16058371+0.j,
        -0.27715263+0.j, -0.16561426+0.j, -0.25473923+0.j, -0.33707132+0.j,
        -0.06265724+0.j, -0.25800425+0.j],
       [-0.41703858+0.j, -0.05644595+0.j, -0.00630538+0.j, -0.23786864+0.j,
        -0.52757124+0.j, -0.30650314+0.j,  0.17194872+0.j,  0.19714238+0.j,
        -0.58572105+0.j, -0.05314466+0.j],
       [ 0.24838216+0.j, -0.34037714+0.j,  0.51189219+0.j, -0.05761980+0.j,
         0.00951487+0.j,  0.31229779+0.j,  0.20983218+0.j,  0.40474594+0.j,
        -0.12901260+0.j, -0.18655516+0.j],
       [-0.12123468+0.j, -0.06620334+0.j, -0.00498805+0.j, -0.05050224+0.j,
        -0.18903222+0.j, -0.06910144+0.j, -0.31557566+0.j, -0.18440393+0.j,
        -0.06776815+0.j, -0.16171303+0.j],
       [ 0.34781631+0.j,  0.30873504+0.j, -0.35114547+0.j,  0.62823533+0.j,
        -0.46557348+0.j, -0.07766555+0.j,  0.10535539+0.j,  0.11320607+0.j,
        -0.00202741+0.j,  0.04976652+0.j],
       [-0.44038110+0.j,  0.07516917+0.j,  0.30560286+0.j,  0.33063321+0.j,
         0.30932336+0.j, -0.37041004+0.j,  0.06554000+0.j, -0.16770823+0.j,
         0.18237494+0.j,  0.08614869+0.j],
       [ 0.17451974+0.j,  0.34350088+0.j,  0.39662734+0.j, -0.23962599+0.j,
        -0.27932937+0.j, -0.17807809+0.j,  0.05717902+0.j, -0.08559187+0.j,
         0.14363800+0.j,  0.22711035+0.j]])