2013-11-01 15 views
7

私は非常に長いベクトル1xr v、非常に長いベクトルw 1xs、および行列A rxsを持っています。これはスパースですが(寸法は非常に大きいです)。Matlabは以下を最適化していませんか?

私はMATLABが最適化されるように、次のように私はメモリとのトラブルに実行されません期待していた:私はので、MATLABは、実際にフルv'*w行列を生成しようとしているよう

A./(v'*w) 

が、それはそうですメモリ不足の問題が発生しています。これを克服する方法はありますか? Aの多くの値が0であるため、すべてv'*wを計算する必要はありません。

EDIT:それができなかった場合は、それを行うための一つの方法は、A(find(A))./(v'*w)(find(A));

を行うことであろうが、あなたが最初にそれを計算し、それをかけることなく、マトリックス(この場合はv'*w)のサブセットを選択することはできません変数。

+1

あなたはおそらく[ 'spfun'](http://www.mathworks.com/help/matlab/ref/spfun.html)の代わりに使用したい - "スパース行列の非ゼロ要素に関数を適用する" –

+0

mmm ... spfunは良いリードかもしれませんが、私はこの場合どのように使用するか分かりません。まず、評価された関数は、それが適用された行列セルのインデックスを知らない。 – kloop

答えて

6
  • bsxfunを使用できます。

    bsxfun(@rdivide, bsxfun(@rdivide, A, v'), w) 
    
  • 別の可能性:これは行列v.'*wを発生させることなくA./(v'*w)と同じ結果を与えるだけゼロ以外の値、使用したい場合:

    [ii jj Anz] = find(A); 
    Anz./v(ii)'./w(jj).' 
    

    これはあなたのA(find(A))./(v'*w)(find(A))に対応する列ベクトルを与えます再びv.'*wを生成せずに。スパース行列A./(v'*w)(ゼロ以外の値の列ベクトルの場合)が必要な場合は、sparse(ii,jj,Anz./v(ii)'./w(jj).')を使用します。

+0

別の 'rdivide'回答!非常に素晴らしい。しかし、メモリの問題のために非ゼロの解決策が必要になるかもしれませんが、もう一度、私が見ているように条件を並べ替えました。 – chappjc

+0

@chappjcはい、私は 'bsxfun'について学んだので、私はすべてにそれを適用する傾向があります:-)私は条件を並べ替えることに関してあなたの点を得ていません –

+0

kloopには'(v '* w) 'がありますが、それらを順番に。一見しただけではわからなかった問題の性質です。結果として、私が試したテストケースでは '5.8208e-11'のリファレンスとは実際には答えが異なります。マシンの精度誤差は累積しますが、まだ小さいです。 – chappjc

関連する問題