Bug #7625

Arrayを継承したオブジェクトのcompactがArrayを返す

Added by Daisuke Furukawa over 1 year ago. Updated about 1 year ago.

[ruby-dev:46807]
Status:Closed
Priority:Normal
Assignee:Yukihiro Matsumoto
Category:core
Target version:2.0.0
ruby -v:ruby 1.9.3p362 (2012-12-25 revision 38607) [x86_64-linux] Backport:

Description

現象:
 ruby 1.9.3で、Arrayを継承したクラスのcompactメソッドを呼び出したとき、
Arrayクラスのオブジェクトが帰ってくる

期待している結果
継承したクラスのオブジェクトが帰ってくる

再現コード

$ ruby -v
ruby 1.9.2p320 (2012-04-20 revision 35421) [i686-linux]
$ irb
irb(main):001:0> class Array2 < Array; end
irb(main):002:0> p Array2.new().compact.class.name

"Array2"

$ ruby -v
ruby 1.9.3p362 (2012-12-25 revision 38607) [x86_64-linux]
$ irb
irb(main):001:0> class Array2 < Array; end
irb(main):002:0> p Array2.new().compact.class.name

"Array"

他に調べたこと

・ruby 1.9.3p327も、p362 と同じ挙動でした
・compactの代わりにuniqを使っても同様の問題が発生
・1.9.3でも、Stringクラスを使って
  s = String2.new().concat("") だとString2クラスのオブジェクトが帰ってきてます

see also: http://blade.nagaokaut.ac.jp/cgi-bin/scat.rb/ruby/ruby-list/49098


Related issues

Related to ruby-trunk - Bug #4136: Enumerable#reject should not inherit the receiver's insta... Closed 12/09/2010
Related to ruby-trunk - Bug #7768: Inherited Array class missing Assigned 02/01/2013

History

#1 Updated by Shugo Maeda over 1 year ago

  • Category set to doc
  • Status changed from Open to Assigned
  • Assignee set to Yukihiro Matsumoto
  • Target version set to 2.0.0

前田です。

mogya@mogya.com (Daisuke Furukawa) wrote:

現象:
 ruby 1.9.3で、Arrayを継承したクラスのcompactメソッドを呼び出したとき、
Arrayクラスのオブジェクトが帰ってくる

この変更自体は、r30148で導入された意図的な変更だと思います。

* array.c (rb_ary_dup): should copy contents only.  no instance
  variable, no class would be copied.  it would affect methods
  #sort, #reject, #transpose, #uniq, #compact, and #shuffle.
  

ただ、まつもとさんが http://bugs.ruby-lang.org/issues/4136#note-7 でflattenなどは
サブクラスのインスタンスを返すという指摘に対し、

If a method is originally defined in Enumerable, i.e. its return value (Array)
is a collection of values from enumerable.
(snip)
I don't think so. #flatten is not an enumerable method. Please point
out if we missed some other methods.

と言っているんですが、compact/uniq/transpose/shuffleもEnumerableでもともと定義されて
いないですよね。
このあたりの一貫性の無さを正当化するような理由はあるでしょうか? > まつもとさん

とくに理由がないのであれば、これらのメソッドはサブクラスのインスタンスを返すようにするか、flattenなども
Arrayを返すようにした方がよいのではないかと思います。

#2 Updated by Shugo Maeda over 1 year ago

  • Category changed from doc to core

#3 Updated by Kenta Murata about 1 year ago

r39004 (#7768) で uniq は修正されたようですね。

#4 Updated by Yukihiro Matsumoto about 1 year ago

Enumerableで定義されていないArray独自のメソッドはサブクラスを返したほうが良いと思います。
直すタイミングはいつがいいのかな。

Matz.

#5 Updated by Motohiro KOSAKI about 1 year ago

Enumerableで定義されていないArray独自のメソッドはサブクラスを返したほうが良いと思います。
直すタイミングはいつがいいのかな。

いまから2.0にspecレベルの変更が入るのは反対します。念のため。

#6 Updated by Usaku NAKAMURA about 1 year ago

結局のところ、1.9.3の挙動は仕様だったのでしょうか?
それとも実はミス?

それによって、trunkに既にcharliesomeが先走って入れちゃった変更を
revertすべきかどうかとか(した方がいいと私個人は強く思っていることを
表明しておきます>mameさん)、1.9.3で現状rubyspecが仕様と思って記述
してしまっているのを変更した上で1.9.3でもバグとして直すべきかどうか、
などといった判断に影響が出ます。

#7 Updated by Yukihiro Matsumoto about 1 year ago

正直なところ、どうして1.9.3と2.0の挙動が異なってしまっているのか経緯を把握してないので適切な答えはできません。
ただ、ArrayにあってEnumerableにないメソッドはレシーバーのクラスを返したほうが良いと思います。

Matz.

#8 Updated by Yusuke Endoh about 1 year ago

matz (Yukihiro Matsumoto) wrote:

正直なところ、どうして1.9.3と2.0の挙動が異なってしまっているのか経緯を把握してないので適切な答えはできません。

#7768 の修正で入った r39004 の副作用で、2.0 の挙動は 1.9.2 の挙動に戻りました。

ただ、ArrayにあってEnumerableにないメソッドはレシーバーのクラスを返したほうが良いと思います。

たまたま現在の挙動が matz の好みということになります。
2.0.0-rc2 はその挙動でいきましょう。それで重大な問題が報告されなければ、p0 もそのままで。
なお、rails 等に影響を与えない公算が高いと思っています (1.9.2 と同じ挙動のはずなので) 。

1.9.3 を変えるかどうかはうささんにお任せします。

Yusuke Endoh mame@tsg.ne.jp

#9 Updated by Yukihiro Matsumoto about 1 year ago

ふむ。まあ、同感なんですが、それはそれとして charliesome には「もうRCだから変更すんな」と釘を刺すべきでは無いですかね。

Matz.

#10 Updated by Usaku NAKAMURA about 1 year ago

こんにちは、なかむら(う)です。

In message " [ruby-trunk - Bug #7625] Arrayを継承したオブジェクトのcompactがArrayを返す"
on Feb.07,2013 23:06:05, matz@ruby-lang.org wrote:

正直なところ、どうして1.9.3と2.0の挙動が異なってしまっているのか経緯を把握してないので適切な答えはできません。

1.9.3と2.0.0はつい先日まで同じでした。
[Bug #7768] を受けて、charliesomeが r39004 でtrunkを変更して
しまったので、挙動に違いが発生しています。

バグなら直すのもやむなしと思いますが、1.9.3では仕様だった(と
これまで理解されてきた)ので、このタイミングで2.0.0の挙動が変
わってしまったことが問題になっています。

ただ、ArrayにあってEnumerableにないメソッドはレシーバーのクラスを返したほうが良いと思います。

同感ですが、いつ、がいいのでしょうね。

それでは。
--
U.Nakamura usa@garbagecollect.jp

#11 Updated by Usaku NAKAMURA about 1 year ago

こんにちは、なかむら(う)です。

In message " [ruby-trunk - Bug #7625] Arrayを継承したオブジェクトのcompactがArrayを返す"
on Feb.07,2013 23:12:55, mame@tsg.ne.jp wrote:

1.9.3 を変えるかどうかはうささんにお任せします。

バグだったのなら1.9.3も当然変えます。
仕様だったのなら当然そのままです。
(中途半端な例があるのは把握してますが)

どっちなんでしょうか...

それでは。
--
U.Nakamura usa@garbagecollect.jp

#12 Updated by Yusuke Endoh about 1 year ago

matz (Yukihiro Matsumoto) wrote:

ふむ。まあ、同感なんですが、それはそれとして charliesome には「もうRCだから変更すんな」と釘を刺すべきでは無いですかね。

IRC で話した感じでは反省してくれてました。
というか、もう RC だから遠藤がもっと監視してる体制でないといけないんですが、全然余力がなくてすみません。
多分明日の晩には ruby20_0 ブランチを切るんで、そこからリリースまではなるべく全コミットを把握するように努めます。

Yusuke Endoh mame@tsg.ne.jp

#13 Updated by Shugo Maeda about 1 year ago

mame (Yusuke Endoh) wrote:

ただ、ArrayにあってEnumerableにないメソッドはレシーバーのクラスを返したほうが良いと思います。

たまたま現在の挙動が matz の好みということになります。

いや、そうなっていないと思います。

$ ./ruby -ve 'class Foo < Array; end; p Foo[2,1,3].sort.class'
ruby 2.0.0dev (2013-02-08 trunk 39154) [i686-linux]
Foo

sortはEnumerableにもあるメソッドなので、まつもとさんの考えでは常にArrayを返す
べきということになると思います。

将来ArrayにしかないメソッドがEnumerableにも追加されたらどうするかとか考える

と、本当にまつもとさんの方針でよいのかもちょっと検討の余地があるように思いますが。

2.0.0-rc2 はその挙動でいきましょう。それで重大な問題が報告されなければ、p0 もそのままで。
なお、rails 等に影響を与えない公算が高いと思っています (1.9.2 と同じ挙動のはずなので) 。

現状まつもとさんの意図が正しく反映されているか疑問ですので、r39004はいったん
revertすべきだと思います。
これがバグ修正扱いなのであれば2.0.0が出た後で直してもよいと思いますし、仕様変更
なのであれば今さら入るのはおかしいのではないですか?

#14 Updated by Motohiro KOSAKI about 1 year ago

2.0.0-rc2 はその挙動でいきましょう。それで重大な問題が報告されなければ、p0 もそのままで。
なお、rails 等に影響を与えない公算が高いと思っています (1.9.2 と同じ挙動のはずなので) 。

現状まつもとさんの意図が正しく反映されているか疑問ですので、r39004はいったん
revertすべきだと思います。
これがバグ修正扱いなのであれば2.0.0が出た後で直してもよいと思いますし、仕様変更
なのであれば今さら入るのはおかしいのではないですか?

議論の余地があるなら問答無用revertに一票。あわてて進めて吉が出ることは少ないよ。

#15 Updated by Shugo Maeda about 1 year ago

#7768の方にもコメントしましたので、議論の続きは(もしあれば)そちらでやりましょう。

#16 Updated by Usaku NAKAMURA about 1 year ago

  • Status changed from Assigned to Closed

#7768 を残してこちらは閉じます。

#17 Updated by Yusuke Endoh about 1 year ago

チケット自体の対処は向こうに書きました通り revert でいいです。
判断が変わってすみません。

以下、言い訳。

2013/02/08 shugo (Shugo Maeda) redmine@ruby-lang.org:

これがバグ修正扱いなのであれば2.0.0が出た後で直してもよいと思いますし、

「実はこれはバグだったんだよ!!」と言って挙動を変えるのは決して
好ましいことではないですよね。今回は matz が希望を明確に言ってる
ので、なるべくその芽を摘んでおきたくて。

もちろんどこかでキリを付ける必要はあるのですが、そのキリは rc2
だと考えている(rc2 までは通常のバグ修正を許可してますし)ので、
現状で行けるなら行きたかったのでした。

(なお rc1 が release candidate の名にそぐわない実体になったのは
スケジュールミスです。これも反省してます)

仕様変更なのであれば今さら入るのはおかしいのではないですか?

言うまでもないので言ってませんが matz だけは別格だと思います。

遠藤は 2.0.0 の変更に対する拒否権を持ってるつもりですが、それは
リリースを円滑に進めることが目的なので、今回はむしろ拒否権を発動
しないほうがリリースが円滑に進むと思ったのでした。
(しかし matz がどのくらい変えたがっているかを読み間違えた感も)

以上、言い訳でした。

とにかく、いろいろ判断誤ったり優柔不断に変えたりしてすみません。
今後もしばしば誤ると思いますが、生温かくご意見ください。

なお、上記の通り rc2 以降は拒否権全開の予定です。

--
Yusuke Endoh mame@tsg.ne.jp

#18 Updated by Shugo Maeda about 1 year ago

前田です。

2013年2月8日 20:15 Yusuke Endoh mame@tsg.ne.jp:

チケット自体の対処は向こうに書きました通り revert でいいです。
判断が変わってすみません。

いえ、了解です。

遠藤さんを責めるつもりはないのですが、一応言い訳にもコメントします。

2013/02/08 shugo (Shugo Maeda) redmine@ruby-lang.org:

これがバグ修正扱いなのであれば2.0.0が出た後で直してもよいと思いますし、

「実はこれはバグだったんだよ!!」と言って挙動を変えるのは決して
好ましいことではないですよね。今回は matz が希望を明確に言ってる
ので、なるべくその芽を摘んでおきたくて。

もちろんどこかでキリを付ける必要はあるのですが、そのキリは rc2
だと考えている(rc2 までは通常のバグ修正を許可してますし)ので、
現状で行けるなら行きたかったのでした。

Redmineを見るかぎり、バグか仕様変更か、また2.0.0で修正すべきかという点について、
まつもとさんが明確に意見表明をしていないという認識でした。
# 「直すタイミングはいつがいいのかな。」とおっしゃってましたし。

まつもとさんから結論が出ているのであれば、反対はしません。

仕様変更なのであれば今さら入るのはおかしいのではないですか?

言うまでもないので言ってませんが matz だけは別格だと思います。

はい、それは理解しています。
しかし、上記のような理由で、今回の件はまだ結論が出ていないという理解でした。
また、まつもとさんの意見は(日本語で書かれたため)charliesomeに届いていませんでしたし。

遠藤さんが各issueの詳細まで把握するのは難しいと思いますので、こういう時は保守的な
判断をしていただいた方がよいのではないかと思います。

--
Shugo Maeda

Also available in: Atom PDF