2

NLTK を使用してかなり大きなデータセットの頻度分布を取得する小さなプログラムがあります。問題は、数百万ワードの後に​​、システムのすべての RAM を使い果たし始めることです。関連するコード行であると私が信じているのは次のとおりです。

freq_distribution = nltk.FreqDist(filtered_words)               # get the frequency distribution of all the words
top_words = freq_distribution.keys()[:10]                       # get the top used words
bottom_words = freq_distribution.keys()[-10:]                   # get the least used words

キー、値ストアをディスクに書き込む方法が必要です。方法がわかりません。私は MongoDB のようなドキュメント ストアから離れ、純粋に Pythonic を維持しようとしています。誰かが何か提案があれば、私はそれをいただければ幸いです。

4

2 に答える 2

6

偶然にも、私は先月同じ問題を抱えていました。NLTK と FreqDist を使用して、大規模なデータセット (英語のウィキペディアとグーテンベルクのデータセットなど) から n グラム頻度表を作成しようとしていました。私の 8GB マシンはユニグラム モデルをメモリに格納できましたが、バイグラム モデルは格納できませんでした。

私の解決策は、ak,v データベースをディスクに保存する BerkeleyDB を使用することでした。速度のためにインメモリ テーブル キャッシュも格納します。度数分布の場合、これは非常に遅いため、FreqDist を使用してメモリ内に独自のサブテーブルも作成し、定期的に (通常は 1000 程度の入力ファイルごとに) BerkeleyDB に保存しました。これにより、多くの重複が削除されるため、BerkeleyDB の書き込みが大幅に削減されます。ユニグラムモデルの「the」は、何十万回も書かれるのではなく、一度だけ書かれます。ここに書きました:

https://www.winwaed.com/blog/2012/05/17/using-berkeleydb-to-create-a-large-n-gram-table/

pickle を使用する際の問題は、ディストリビューション全体をメモリに格納する必要があることです。純粋に Pythonic である唯一の方法は、独自の k,v ディスク データベースと、おそらく独自のインメモリ キャッシュを使用して、独自の実装を作成することです。BerkeleyDB の使用は、非常に簡単で効率的です。

于 2012-05-27T13:28:45.790 に答える
2

I've used the JSON module to store large dictionaries (or other data structures) in these kinds of situations. I think pickle or cpickle may be more efficient, unless you want to store the data in human-readable form (often useful for nlp).

Here's how I do it:

import json
d = {'key': 'val'}
with open('file.txt', 'w') as f:
    json.dump(d, f)

Then to retrieve,

with open('file.txt', 'r') as f:
    d = json.loads(f.read())
于 2012-05-27T05:51:29.977 に答える