2

いくつかの Clojure コードのストレス テストを行っているときに、大規模なデータ セットを反復処理しているときにヒープ領域が不足していることに気付きました。私は最終的に、Clojure のdoseq機能と遅延シーケンスの実装の組み合わせに問題を突き止めることができました。

これは、使用可能なヒープ領域を使い果たして Clojure をクラッシュさせる最小限のコード スニペットです。

(doseq [e (take 1000000000 (iterate inc 1))] (identity e))

のドキュメントにdoseqは、遅延シーケンスの先頭を保持しないことが明確に記載されているため、上記のコードのメモリの複雑さは O(1) に近いと予想されます。足りないものはありますか?非常に大きな遅延シーケンスを繰り返し処理する Clojure の慣用的な方法は何doseqですか?

4

1 に答える 1

2

このサンプルを実行すると、メモリ使用量が 2.0 ギガに達したので、実際には RAM が不足している可能性があります。

確かに実行には時間がかかります:

user=> (time (doseq [e (take 1000000000 (iterate inc 1))] (identity e)))
"Elapsed time: 266396.221132 msecs"

フォームトップ:

23999 arthur    20   0 4001m 1.2g 5932 S  213 15.3  17:11.35 java                                          
24017 arthur    20   0 3721m 740m 5548 S   88  9.3  13:49.95 java  
于 2012-08-13T22:35:15.880 に答える