From: Takashi Ikeda Date: 1999-10-27T00:29:28+09:00 Subject: [ruby-dev:8123] Re: [ruby-list:17940] Enumerable#collect 池田孝志です。 僕の言った事に対してだけ返答します。 EGUCHI Osamu writes: > えぐち@エスアンドイー です。 > > >>> In message [ruby-dev:8110] Re: [ruby-list:17940] Enumerable#collect > On Sun, 24 Oct 1999 07:12:34 +0900, nobu.nakada@nifty.ne.jp said: > > なかだ> なかだです。 > なかだ> > なかだ> At Sat, 23 Oct 1999 22:07:33 +0900, > なかだ> EGUCHI Osamu wrote: > > なかだ> > return self.dup if self.is_a? Array > なかだ> > > なかだ> > に相当する部分が、がありませんが、 > なかだ> > ここの dup の必要性は議論の余地がありますね。 > なかだ> > ここに dup が要るのであれば、 Array#to_a にも > なかだ> > dup が要る様な気がします。 > なかだ> > なかだ> to_a/collect は必ず新しい Array に push していきますから dup は > なかだ> いらないと思います。 > > この、 『Array#to_a にもdup が要る様な気がします。』は、 > > % ruby -v > ruby 1.4.2 (1999-09-18) [i386-freebsd3.3] > % ruby -e 'a=[];b=a.to_a;p a.equal? b' > →true > % > > の様な状況の事を言っています。 > > あと、大概の to_a / collect は新しい Array に push しているので、 > dup は不要と言うのは同感ですが、 > > return self.dup if self.is_a? Array > > では、「大概の」ではなく、Array#collect を特別扱いしています。 大体、[ruby-dev:8090]自体バグっていることはともかく、これを 出した段階では、Enumerable#to_aを知らなかったのであえてこう していました。意図は汲んでもらえるとして、 > まぁ、効率にしか影響しないし、必ずしも速くなる場合だけでもなようです。 ですが、Array#collectをArray#to_aのdupを取ったものの代わりと して利用するには、[ruby-dev:8090]時点の僕には酷でした。 % ruby -v ruby 1.4.2 (1999-09-18) [i586-linux] % ruby -e ' a = Array.new(1000_000) GC.start t = Time.now a.collect {|e| e } p Time.now - t GC.start t = Time.now a.to_a p Time.now - t ' 279.01583 8.6e-05 [ruby-dev:8090]はEnumerable#to_aを知らない段階で作ったので、 [ruby-dev:8090]のcollectがEnumerable#to_aをdupしたものと同じ 結果を出すようにしか考えていません。よってレシーバにArrayが やってきたときには、yieldのぶん速くした方がよいのではないか という提案でした。 判定でちょっと遅くなるくらいなら、相当遅くなるのを回避した方 が良いか、と思ったので。 もちろん、これがあまり要らないと僕が感じている事は、 [ruby-dev:8090]に書いたとおりです。 Array#to_aでは(ソースとしては)レシーバを返すという仕様がある、 という点も知らなかったので、えぐちさんが入る前の [ruby-dev:8098]で僕は[ruby-dev:8090]のcollectを Enumerable#to_aと等価と考えていました。今のto_aから得たオブ ジェクトを[ruby-dev:8090]のcollect として動作させるには、dup しないといけないようです。[ruby-dev:8090]の*1つ目の*collect には、やはりこのような二度手間はさせたくありません。 # もちろん、僕はArray#to_aをdupさせたいと思ったことは*今も* # ありません。 -- 池田 孝志 cercine@kcn.ne.jp