ビッグデータでSVDとPCAを行う方法は?


29

大量のデータセット(約8 GB)があります。機械学習を使用して分析したいと思います。したがって、SVDを使用してからPCAを使用して、効率のためにデータの次元を減らす必要があると思います。ただし、MATLABとOctaveはそのような大きなデータセットを読み込むことができません。

このような大量のデータでSVDを実行するために使用できるツールは何ですか?


こんにちは、DSへようこそ!おそらく、データセットについて少し詳しく説明できます。行と列はいくつありますか?これは、考えられるソリューションに影響を与える可能性があります。
S. Kolassa -復活モニカ

23711341行、8列。私は1-2列を削除しようとすることができます。それらは私の問題に関係していないようです。
デビッドS. 14

ここで列の前に行をサンプリングする必要があります。データサイズを削減するために行をランダムにサンプリングできない理由はありますか?私はここで行がユーザーか何かに関連していると仮定しています
cwharland

自分自身を明確にしないとすみません。私の目標はPCAを行うことです。サンプルデータのSVDは、PCAを行うのに役立つとは思いませんか?
デビッドS. 14

PCAは通常、共分散行列でSVDを計算することにより実装されます。共分散行列の計算は恥ずかしいほど並列のタスクなので、レコードの数に応じて簡単にスケーリングできます。
アノニムース14

回答:


41

まず、多くの共変次元があり、データポイントを新しい直交基底に回転させ、分散が最大の軸のみを取得することで問題のサイズを削減する場合、次元削減が使用されます。8つの変数(列)を使用すると、スペースはすでに低次元であるため、変数の数をさらに減らしてもメモリサイズに関する技術的な問題を解決することはできませんが、データセットの品質に大きく影響する可能性があります。あなたの具体的なケースでは、オンライン学習を見ることがより有望ですメソッド。大まかに言って、これらのメソッドはデータセット全体を操作する代わりに、それらの一部(多くの場合「ミニバッチ」と呼ばれる)を一度に取得し、インクリメンタルにモデルを構築します。(個人的には、「オンライン」という単語を、データセット全体を一度にロードできないTwitterフィードのようなインターネットからの無限に長いデータソースへの参照として解釈したい)。

しかし、メモリに収まらないデータセットにPCAのような次元削減手法を本当に適用したい場合はどうでしょうか?通常、データセットはサイズn x mのデータ行列Xとして表されます。ここで、nは観測値(行)の数、mは変数(列)の数です。通常、メモリの問題は、これら2つの数値のうちの1つのみに起因します。

観測値が多すぎる(n >> m)

観測値多すぎるが、変数の数が小さいものから中程度の場合、共分散行列をインクリメンタルに作成できます。実際、典型的なPCAは、サイズm x mの共分散行列を構築し、それに特異値分解を適用することから成ります。M型のfloat64の= 1000個の変数、共分散行列は、SVDと共に使用することができるメモリすっぽり入ると、サイズが1000×1000×8〜8Mバイトを有しています。したがって、データセット全体をメモリにロードせずに共分散行列を構築するだけで済み、非常に扱いやすいタスクです。

または、データセットから小さな代表サンプルを選択し、共分散行列近似することができます。このマトリックスは、通常とまったく同じプロパティを持ちますが、わずかに精度が低下します。

変数が多すぎる(n << m)

一方、変数多すぎる場合、共分散行列自体がメモリに収まらないことがあります。たとえば、640x480の画像を使用する場合、すべての観測には640 * 480 = 307200の変数があり、結果として703Gbの共分散行列が生成されます。それは間違いなく、コンピューターのメモリーやクラスターのメモリーに保持したいものではありません。したがって、共分散行列をまったく構築せずに次元を削減する必要があります。

私のお気に入りの方法はランダム投影です。要するに、サイズn x mのデータセットXがある場合、サイズm x kのスパースランダム行列Rk << m)で乗算し、より小さなサイズn x kの新しい行列X 'を取得できます。元のプロパティほぼ同じプロパティで。なぜ機能するのですか?まあ、PCAは直交軸(主なコンポーネント)のセットを見つけて、データを最初のkそのうちの。スパースランダムベクトルはほぼ直交しているため、新しい基礎として使用することもできます。

そして、もちろん、あなたは、データセット全体を乗算する必要はありませんXのことでRあなたはすべての観測翻訳することができます- Xを個別に新しい基礎にまたはミニバッチで。

Random SVDと呼ばれる同様のアルゴリズムもあります。実際の経験はありませんが、ここで説明付きのサンプルコードを見つけることができます。


一番下の行として、大きなデータセットの次元削減のための短いチェックリストを示します。

  1. ディメンション(変数)がそれほど多くない場合は、単にオンライン学習アルゴリズムを使用してください。
  2. 多くの観測値があるが、適度な数の変数(共分散行列がメモリに収まる)の場合、行列を増分的に構築し、通常のSVDを使用します。
  3. 変数の数が多すぎる場合は、増分アルゴリズムを使用します。

3
全体として、私はあなたの答えが好きですが、冒頭の文はまったく正しくありません。PCAは、低分散の多くの次元には適していません。むしろ、相関する分散を持つ多くの次元に適しています。特定のデータセットでは、すべての次元で分散が大きくなる可能性がありますが、高い共分散がある限り、PCAは次元の大幅な削減を実現できます。
ボガトロン

1
@bogatron:良いキャッチ、ありがとう。実際、私はいくつかの次元で、おそらく元の次元ではなく、高/低分散に言及していました。たとえば、この図では、これらの寸法は元のx / y軸ではなく、2つの矢印で定義されています。PCAは、これらの新しい軸を見つけようとし、各軸に沿った分散の値で並べ替えます。とにかく、あなたが指摘したように、それは悪い言葉遣いだったので、私は私の考えを再定式化しようとしました。うまくいけば、より明確になりました。
ffriend 14

それは理にかなっています。+1。
bogatron 14

7

気にしないでください。

プログラミングの最初のルール-データサイエンスにも適用されます:すべてを小さなテスト問題で動作させます。

たとえば、100,000行のデータのランダムサンプルを取得します。別のアルゴリズムなどを試してみてください。すべてが満足のいくものになったら、より大きな(より大きな)データセットを試してみてください-データを追加するにつれてテストエラーがどのように減少するかを確認してください。

さらに、svdを8列のみに適用したくない場合は、列が多いときに適用します。


1
+1は、svdを8列のみに適用したくない場合です。多数の列がある場合に適用します。
S. Kolassa -復活モニカ

6

PCAは通常、共分散行列でSVDを計算することにより実装されます。

共分散行列を計算することであるあきれるほど並列それはスケールので、タスクリニアレコード数とし、複数のマシンに配布するのは簡単です!

データを1回渡すだけで、平均を計算できます。次に、共分散行列を計算するための2番目のパス。これはmap-reduceで簡単に実行できます-基本的には、平均を再度計算するのと同じです。共分散のような合計項は、並列化するのは簡単です!同様の大きさの多くの値を合計するときは、数値にのみ注意を払う必要があります。

膨大な数の変数がある場合、状況は異なります。ただし、8 GBシステムでは、BLASライブラリを使用して、メモリ内で最大20.000次元でPCAを実行できます。しかし、PCAの自由度が多すぎるため、PCAの信頼性が低下するという問題に直面する可能性があります。つまり、簡単にオーバーフィットします。少なくとも10 * d * dレコード(またはd ^ 3)を記録することをお勧めします。したがって、10000次元の場合、結果が統計的に信頼できるようにするには、少なくとも1億のレコード(10000次元の...それはたくさんです!)が必要です。


1

おそらく、1台のマシンで実行できるツールをいくつか見つけることができますが、Sparkのような「ビッグデータ」ツールを検討するのが理にかなっています。Sparkには、PCAとSVDをサポートするMLlibというコンポーネントがあります。ドキュメントには例があります。



0

わずかなメモリフットプリントを持つファイルを遅延評価し、numpy / scipyがOctave / Matlabが提供するすべてのツールへのアクセスを提供する場合、Pythonをお勧めします。

弊社のサイトを使用することにより、あなたは弊社のクッキーポリシーおよびプライバシーポリシーを読み、理解したものとみなされます。
Licensed under cc by-sa 3.0 with attribution required.