2007-03-12
Ruby builtin in pure Ruby
[Update 03/12/2007 If you know how to implement Interge#times in pure ruby and make it have the same behavior as Ruby 1.8.5, please let me know. Thank you!]
One of the best things I love about rubinius project is: their developers try to keep the dependency on system language (C in their case) minimal, and they take it seriously. Take a look of http://code.fallingsnow.net/svn/rubinius/trunk/kernel/core/, you will find out lots of buitlin libraries are implemented in pure ruby, even lots of string functions.
Pure ruby builtin has some drawbacks, though. One is performance penalty, the other is potential side effects. For example, basically Integer#times can be implemented as simple as this in pure ruby:
But this version of Integer#times does not work exactly the same as Ruby 1.8.5. If an user want to override Fixnum#+ (this may never happen in real life):
Our Integer#times's behavior will change, while Ruby 1.8.5 won't. That is because Ruby 1.8.5's implementation (int_dotimes() in Numeric.c) optimizes for Fixnum: it does not call '+' method dynamically for Fixnum, instead, it just increases the integer directly. If you want to implement this method as same as Ruby 1.8.5 then you have to write code in system language.
This kind of optimization is all over the place in c ruby. I am not clear about its motivation, but I guess performance is one of the reasons. For example, "30000000.times {|x|}" is about twice faster than "i = 0; while i < 30000000; i +=1; end" in Ruby 1.8.5.
Difference people may have different opinions on what the 'right' behavior should be. As for me, I like the behavior of the pure ruby implementation better.
One of the best things I love about rubinius project is: their developers try to keep the dependency on system language (C in their case) minimal, and they take it seriously. Take a look of http://code.fallingsnow.net/svn/rubinius/trunk/kernel/core/, you will find out lots of buitlin libraries are implemented in pure ruby, even lots of string functions.
Pure ruby builtin has some drawbacks, though. One is performance penalty, the other is potential side effects. For example, basically Integer#times can be implemented as simple as this in pure ruby:
class Integer
def times
i = 0
while i < self
yield i
i += 1;
end
self
end
end
But this version of Integer#times does not work exactly the same as Ruby 1.8.5. If an user want to override Fixnum#+ (this may never happen in real life):
class Fixnum
def + x
return 9999
end
end
Our Integer#times's behavior will change, while Ruby 1.8.5 won't. That is because Ruby 1.8.5's implementation (int_dotimes() in Numeric.c) optimizes for Fixnum: it does not call '+' method dynamically for Fixnum, instead, it just increases the integer directly. If you want to implement this method as same as Ruby 1.8.5 then you have to write code in system language.
This kind of optimization is all over the place in c ruby. I am not clear about its motivation, but I guess performance is one of the reasons. For example, "30000000.times {|x|}" is about twice faster than "i = 0; while i < 30000000; i +=1; end" in Ruby 1.8.5.
Difference people may have different opinions on what the 'right' behavior should be. As for me, I like the behavior of the pure ruby implementation better.
发表评论
- 浏览: 12171 次

- 详细资料
搜索本博客
最新评论
-
gem.config的一个小问题
haha, 正是我想要的。 谢谢!
-- by yawl -
gem.config的一个小问题
config.gem 'solr-ruby', :lib => 'solr'
-- by rainux -
最近的ruby的vulnerabilit ...
robbin 写道哈哈,原来是一个项目,那肯定需要做一些代码方面的修改,无可避免 ...
-- by neodoxy -
最近的ruby的vulnerabilit ...
哈哈,原来是一个项目,那肯定需要做一些代码方面的修改,无可避免的。
-- by robbin -
最近的ruby的vulnerabilit ...
robbin 写道neodoxy 写道Quake Wang 写道phoenix5 ...
-- by neodoxy






评论排行榜