From: dblack@... Date: 2006-03-03T11:07:12+09:00 Subject: Re: Nuby - why does my #inspect misbehave? Hi -- On Fri, 3 Mar 2006, cremes.devlist@mac.com wrote: > I'm working through a few exercises to teach myself Ruby. One of them is the > creation of a deck of cards along with all the usual operations one performs > upon them. > > I override the Object#inspect method to pretty-print my card values, but it > doesn't always get called. Whether or not it gets called depends on the > **absence** of a line in #print_playing_deck. Here is my code stripped down > to the basics. > > class Card < Object Don't inherit from Object -- it happens automatically :-) > def inspect > puts "#{self.value} of #{self.suit}s" > end This is having a weird effect on what you get in irb, like when you create a deck, you get: of s because it's trying to print that string. #inspect should really just return a string, not print it out (as I think Logan also mentioned). > def print_playing_deck > @playing_deck.each do |card| > puts card > end One of the great rites of passage for new Rubyists is learning that: puts array does the iterating for you :-) So that should be just: puts @playing_deck > # WEIRD!! If I have any code after this loop, my Card#inspect is not > called. > # In this case I have a "puts" but it could even be arithmetic expressions > preventing > # the #inspect from working > #puts "#{@playing_deck.length} cards in deck" > end > end > > And here is the output: > > > irb(main):001:0> load 'ex.rb' > => true > irb(main):002:0> d=CardDeck.new(5) > of s > => > irb(main):003:0> d.print_playing_deck > # > # > # > # > # > 5 cards in deck > => nil That nil is the return value of puts, which is the last expression in #print_playing_deck. > ######## comment out the "puts" in #print_playing_deck and reload > irb(main):004:0> load 'ex.rb' > ./ex.rb:22: warning: already initialized constant SUITSIZE > => true > irb(main):005:0> d.print_playing_deck > # > # > # > # > # > 1 of Hearts > 2 of Hearts > 3 of Hearts > 4 of Hearts > 5 of Hearts > => [, , , , ] Now the last expression in #print_playing is @playing_deck (the return value of the call to #each). To display @playing_deck, irb calls #inspect on each element. The side-effect of this is that "1 of Hearts" etc. gets printed. The return value of #inspect, however, is nil (the value of puts), which is why you get the weird little array of nothings at the end. David -- David A. Black (dblack@wobblini.net) Ruby Power and Light (http://www.rubypowerandlight.com) "Ruby for Rails" chapters now available from Manning Early Access Program! http://www.manning.com/books/black