Prev: State of the union for Ruby CLI libraries?
Next: [ANN] Rack 1.2, a modular Ruby webserver interface
From: Michał Zając on 13 Jun 2010 13:27 Hello, I write in ruby for few weeks and I have noticed that in ruby I use class (static) methods more often than in "traditional" languages like java or c#. In java I use instance methods for two purposes - maintaining object state and to use polymorphic behaviour. In ruby polymorphism is available to class methods as well as for instance ones so I don't see need for using instance methods in stateless classes (for example typical application / domain services). It is common for ruby programmers or maybe I have miss something? Best Regards, Michał
From: Rein Henrichs on 13 Jun 2010 22:05 On 2010-06-13 10:27:48 -0700, Michał Zając said: > Hello, > I write in ruby for few weeks and I have noticed that in ruby I use > class (static) methods more often than in "traditional" languages like > java or c#. In java I use instance methods for two purposes - > maintaining object state and to use polymorphic behaviour. In ruby > polymorphism is available to class methods as well as for instance ones > so I don't see need for using instance methods in stateless classes > (for example typical application / domain services). > > It is common for ruby programmers or maybe I have miss something? > > Best Regards, > Michał Classes are designed to instantiate objects. If you have classes that consist solely of class methods then they aren't functioning as classes at all but rather as convenient globally-available namespaces for singleton methods, which is a very procedural style of progrmaming. Procedural programming is not necessarily bad, but you are missing out on a great deal of the power and flexibility of an OOP langauge by writing procedural code. Then again, if the system works for you and maintainability and other core values do not appear to suffer, who's to say you're doing it wrong? Even asking the question shows that you're thinking critically about the tradeoffs involved here, which is a good start. -- Rein Henrichs http://puppetlabs.com http://reinh.com
From: Robert Klemme on 14 Jun 2010 09:33 2010/6/14 Rein Henrichs <reinh(a)reinh.com>: > On 2010-06-13 10:27:48 -0700, MichaÅ ZajÄ c said: > >> I write in ruby for few weeks and I have noticed that in ruby I use class >> (static) methods more often than in "traditional" languages like java or c#. >> In java I use instance methods for two purposes - maintaining object state >> and to use polymorphic behaviour. In ruby polymorphism is available to class >> methods as well as for instance ones so I don't see need for using instance >> methods in stateless classes (for example typical application / domain >> services). >> >> It is common for ruby programmers or maybe I have miss something? > > Classes are designed to instantiate objects. If you have classes that > consist solely of class methods then they aren't functioning as classes at > all but rather as convenient globally-available namespaces for singleton > methods, which is a very procedural style of progrmaming. Procedural > programming is not necessarily bad, but you are missing out on a great deal > of the power and flexibility of an OOP langauge by writing procedural code. As a compromise Michael could use module Singleton and thus define instance methods without the overhead of creating new instances all the time. irb(main):001:0> require 'singleton' => true irb(main):002:0> class Foo;end => nil irb(main):003:0> (1..3).map { Foo.new } => [#<Foo:0x1029b494>, #<Foo:0x1029b478>, #<Foo:0x1029b45c>] irb(main):004:0> class Foo; include Singleton; end => Foo irb(main):005:0> (1..3).map { Foo.new } NoMethodError: private method `new' called for Foo:Class from (irb):5:in `block in irb_binding' from (irb):5:in `each' from (irb):5:in `map' from (irb):5 from /opt/bin/irb19:12:in `<main>' irb(main):006:0> (1..3).map { Foo.instance } => [#<Foo:0x10268b88>, #<Foo:0x10268b88>, #<Foo:0x10268b88>] irb(main):007:0> Singleton pattern allows for easier migration if at a later point in time instances need state. > Then again, if the system works for you and maintainability and other core > values do not appear to suffer, who's to say you're doing it wrong? Even > asking the question shows that you're thinking critically about the > tradeoffs involved here, which is a good start. Absolutely agree! Kind regards robert -- remember.guy do |as, often| as.you_can - without end http://blog.rubybestpractices.com/
From: Michał Zając on 14 Jun 2010 13:35 W dniu 2010-06-14 15:33, Robert Klemme pisze: > > As a compromise Michael could use module Singleton and thus define > instance methods without the overhead of creating new instances all > the time. > I think this is interesting idea. I have spent much time in Java / C# environments with heavy use of dependency injection pattern so maybe this is source of my aversion to stateless classes manual instantiation - usually something else has done it for me :D Using Singleton pattern is more similar to Service Locator but it may be good alternative. Thanks
From: Rein Henrichs on 14 Jun 2010 19:06 On 2010-06-14 10:35:10 -0700, Michał Zając said: > W dniu 2010-06-14 15:33, Robert Klemme pisze: >> >> As a compromise Michael could use module Singleton and thus define >> instance methods without the overhead of creating new instances all >> the time. >> > > I think this is interesting idea. > I have spent much time in Java / C# environments with heavy use of > dependency injection pattern so maybe this is source of my aversion to > stateless classes manual instantiation - usually something else has > done it for me :D Using Singleton pattern is more similar to Service > Locator but it may be good alternative. > > Thanks Ruby's design patterns (in the Gang of Four sense) are extremely lightweight compared to their Java equivalents. Rick Olsen's Design Patterns in Ruby book shows good idiomatic Ruby implementations of the GoF patterns. That said, I don't think you want a Pattern at all. I think you want a more *object oriented* architecture. IRT Singleton: I think that Singleton is just a way to cheat and get global state that looks like instances. I didn't present it as a solution because (imo) it's really just a restatement of the problem. I try to avoid it for the same reasons that I try to avoid the classes you're asking about. Let me put it this way: replace all of your pseudo-classes (these classes that don't instantiate and are used as singleton method holders) with this: YourClass = Object.new def YourClass.some_method ... do stuff ... end .... more ... This is functionally equivalent. Does this look like good Ruby code? Is this good OO design? If not, why not? The classes you're asking about aren't (functionally) classes at all: they're just objects like this one. You should object to them for the same reasons that you (may) object to the above. Also, Ruby has far better mechanisms than dependency injection. So much so, in fact, that Rails core member and creator of two different Ruby dep. injection libraries, Jamis Buck, recently gave a great talk about why you don't need dependency injection in Ruby. Summary is here, and is a good read if you're coming from heavy, "enterprisey" languages like Java: http://weblog.jamisbuck.org/2008/11/9/legos-play-doh-and-programming. Coming from a Java background, the best thing you can do is let go of the heavy pattern-driven architectures that are common in enterprise-land (the ServiceLocator, CachedTemplateFactoryProxyFactory, whatever) and enjoy the freedom of working with simple, lightweight classes and objects. -- Rein Henrichs http://puppetlabs.com http://reinh.com
|
Next
|
Last
Pages: 1 2 Prev: State of the union for Ruby CLI libraries? Next: [ANN] Rack 1.2, a modular Ruby webserver interface |