From: Akinori MUSHA Date: 2013-07-17T10:38:58+09:00 Subject: [ruby-dev:47516] Re: Hash#to_hashがHashを返さない --pgp-sign-Multipart_Wed_Jul_17_10:29:12_2013-1 Content-Type: text/plain; charset=ISO-2022-JP At Wed, 17 Jul 2013 08:26:03 +0900, xibbar wrote: > 表題はちょっぴりあおり気味ですが、 > RubyのHash#to_hashはHashを返さずにselfを返します。 > Hashのまま使っているんだったらいいのですが、 > これを継承すると、 > % irb > irb(main):001:0> class MyHash => nil > irb(main):002:0> myhash=MyHash.new > => {} > irb(main):003:0> myhash.to_hash > => {} > irb(main):004:0> myhash.to_hash.class > => MyHash > となってしまいます。 > これ、Array#to_aやString#to_sだと > ArrayとStringをそれぞれ返します。 > > Hash#to_hashはHashを返したほうがいいのではないでしょうか? > 現状、継承したHashからHashを得るためには > Hash[myhash]とやるのが正解のようで、 > これはこれで裏技に近いと思いました。 Array#to_a に相当するのは Hash#to_h です。こいつは継承してもHashを返し ますよ。myhash.to_h でOKのはず。 to_str/to_ary/to_hash とフルネームの変換メソッドは、本当にそれぞれ String/Array/Hash に暗黙の変換もしてほしいというとき「だけ」、それぞれ のクラスのインスタンスを返すように(再)定義すべしというのが決まりです。 (Rubyでは Klass.try_convert, C APIでは rb_convert_type()等で暗黙に使わ れるため) 従って、必要なら継承した上で to_hash を再定義すべき(単純なケースなら alias to_hash to_h)というのが模範解答だと思います。 ただ、 Array#to_a/to_ary はそうなっているけど String#to_s/to_str はそう ではないようです。おそらく、 String を継承するのは String の拡張した何 かを作りたいケースなので String への自動変換は望まれることが自然だが、 Array/Hash はコンテナであり、拡張というよりは内包するより楽なので継承す るというケースが多いので自動変換は必ずしも望まれないということなのかな というのが私の推測です。 -- Akinori MUSHA / http://akinori.org/ --pgp-sign-Multipart_Wed_Jul_17_10:29:12_2013-1 Content-Type: application/pgp-signature Content-Transfer-Encoding: 7bit -----BEGIN PGP SIGNATURE----- Version: GnuPG v1.4.13 (FreeBSD) iEYEABECAAYFAlHl82gACgkQkgvvx5/Z4e4a6QCfTXqQwyiL6tXQzxG+g5X1DNIA u1gAnRpoKIMJmsBzFASr+YHoBKYsQxxX =ogLc -----END PGP SIGNATURE----- --pgp-sign-Multipart_Wed_Jul_17_10:29:12_2013-1--