From: Cees Zeelenberg Date: 2012-07-01T22:15:18+09:00 Subject: Re: Interactions between 'new' and 'initialize' ? Many thanks for all the contributions. Let me first try to explain a little bit further why I wanted tho change the 'new' class method. I have recently implemented a set of JRuby bindings for the QtJambi Library. QtJambi is the Java version of the Qt GUI framework, a cross-platform application development toolkit. The library consists of several hundred Java classes and Interfaces. In JRuby these can all be accessed through the Qt:: namespace. Classes and Modules are 'lazily' loaded when they are accessed through the 'const_missing' method. In this method a constant is assigned to the underlying Java Class and a class method 'new' is defined similar to the one mentioned in one of the postings: def new(*a,&b) instance=self.allocate instance.send(:initialize,*args) if block_given? if block.arity == -1 || block.arity == 0 instance.instance_eval(&block) elsif block.arity == 1 block.call(instance) else raise ArgumentError, "Wrong number of arguments to block(#{block.arity} ; should be 1 or 0)" end end return instance end The underlying object is an instance of a Java Class, sending an initialize method is the equivalent of Ruby 'initialize'. JRuby takes care of a great deal of 'type' conversions between Ruby and Java. The 'new' method also implements an optional Ruby Initializer Block. Various other things take place upon loading the Java Class, but they are not directly relevant to this discussion. Anyone actually interested in the code can download it from http://github.com/CeesZ/qt_connect or get the Gem: gem install qt_connect This takes care of a basic API with access to all Classes and Interfaces( Modules) in the Qt toolkit. The Java Classes can be extended with Ruby methods or inherited by Ruby Classes. Bindings to the Qt toolkit for Ruby (not JRuby) have been available for many years. Since these bindings and the QtJambi library are based on the same underlying C++ library the resulting API's are very similar, but not quite the same. To improve compatibility (and program portability) between the two implementations, I have also added a compatibility layer, which basically patches individual classes when they are loaded. These patches are mostly mutations to the input arguments which can be done by simple Ruby wrappers round the relevant Java Methods. This works well in practice and many QtRuby programs can now run unchanged on both platforms. I ran into a problem however when the arguments of the constructor have to be patched. I implemented that by wrapping the 'new' method (since that is already a Ruby Method; the initializer is not). This works fine for the base class, but causes problems for inherited classes as described in the initial posting. As far as I can see it, my best bet to solve this problem is to provide Ruby wrappers for the 'initialize' methods and to apply any patches there. Thanks to the posting of Robert Klemme I understand better what happens when changing a 'new' class method, but I can't say I fully understand it, so it seems safer not to interfere. For those interested, I found also a paragraph (13.1.4 Class methods in -even more- depth) in The Well-Grounded Rubyist from David Black, on the special behavior on singleton methods defined on objects of class Class. == Cees Zeelenberg -- Posted via http://www.ruby-forum.com/.