Ruby Array#puts not using overridden implementation?

拟墨画扇 提交于 2019-12-11 23:02:27

问题


I am using Ruby 1.8.6 for the following code:

# Create an array and override the #to_s on that object
thing = [1,2,3]
def thing.to_s
  'one'
end

print "Using print: "
print thing

puts
puts "Using puts: "
puts thing

Output:

Using print: one
Using puts: 
1
2
3

So thing is an Array and I have overridden thing#to_s. print seems to use my overriden implementation while puts does not. Why?

I have followed the source code of Kernel#puts and Kernel#print (which are C-implementations) and see that they are very different implementations. I want to know what might be the design-decision (if any) behind this?

By the way, if I create thing as an instance of another class I wrote (or as a Hash/String/other-classes I tried), both print and puts use the overridden implementation of to_s.


回答1:


From the Ruby Programming Language:
alt text http://ecx.images-amazon.com/images/I/41n-JSlBHkL._SL75_.jpg

Output streams are appendable, like strings and arrays are, and you can write values to them with the << operator. puts is one of the most common output methods. It converts each of its arguments to a string, and writes each one to the stream. If the string does not already end with a newline character, it adds one. If any of the arguments to puts is an array, the array is recursively expanded, and each element is printed on its own line as if it were passed directly as an argument to puts. The print method converts its arguments to strings, and outputs them to the stream. If the global field separator $, has been changed from its default value of nil, then that value is output between each of the arguments to print. If the output record separator $/ has been changed from its default value of nil, then that value is output after all arguments are printed.

As for design decisions, that I do not know.




回答2:


Oh boy ... This has already been the topic of a countless number of endless threads on the ruby-talk mailinglist, the ruby-core mailinglist and a gazillion of blogs.

The gist of it is that puts special cases Arrays. Why it special cases those, why it special cases only those (as opposed to, say, all Enumerables), why it special cases those (and not, say, print), nobody really knows. It is the way it is.

BTW, since you mentioned the POLS: the Ruby community has always made it very clear that the POLS only applies to matz. So, Ruby is about not surprising matz. If you or me or anybody else is surprised, that doesn't count.



来源:https://stackoverflow.com/questions/1977874/ruby-arrayputs-not-using-overridden-implementation

标签
易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!