From: Nobuyoshi Nakada Date: 2008-08-20T12:13:59+09:00 Subject: [ruby-dev:35883] Re: Refactoring of enumerating prime numbers なかだです。 At Wed, 20 Aug 2008 11:52:55 +0900, 石塚圭樹 wrote in [ruby-dev:35882]: > >Prime.instance.eachというのは冗長に感じます。どうせならそのイン > >スタンス自体をPrimeという定数にしてはどうでしょうか。 > > 私もそうなのかなぁ? と思いつつも, では, 元のクラスの名前はどうするんだ? > と思ったりもしてます. class << (Prime = Object.new); end で。 > >Prime.eachを追加するだけでいいような気もしなくはないです。 > これって, Yugui さんの第2案: > と近いですが, include Enumerable が入っていません. Enuerable である必 > 要はなく each だけあればよいってことです? Enumerableは入れ忘れですが、Generatorのように別クラスを介する必 要はないのではないかということです。 > あと, 別件で気になっていることが... 現行でもそうですが, 結構重要なク > ラス変数の使われ方をしています. これらのクラス変数の組を概念的に取りま > とめたクラスというものも考えられそうと言う気がしています. それがPrime自身の役割なんじゃないかなぁと。 > また, 微妙にスレッドセーフでない気もしたりもしているので, そこも解消で > きればなぁ. などと思ったりしています そこは問題ですね。Prime#succのループをsynchronizeさせればいいで しょうか。 ひとまず、Prime関係を別ファイルに切り分けるところまでやってしまっ てはどうでしょうか。 Index: lib/mathn.rb =================================================================== --- lib/mathn.rb (revision 18717) +++ lib/mathn.rb (working copy) @@ -60,4 +60,5 @@ class Prime # n < Math.sqrt(@@next_to_check) }) @@ulticheck_next_squared = 121 # @@primes[@@ulticheck_index + 1] ** 2 + @@lock = Mutex.new class << self @@ -82,4 +83,6 @@ class Prime def succ @index += 1 + if @index >= @@primes.length + @@lock.synchronize do while @index >= @@primes.length # Only check for prime factors up to the square root of the potential primes, @@ -97,4 +100,6 @@ class Prime @@next_to_check += 2 end + end + end return @@primes[@index] end -- --- 僕の前にBugはない。 --- 僕の後ろにBugはできる。 中田 伸悦