Newbie, to_s question

(EdUarDo) #1

Hi all, I have this class:

class Tactic
     attr_reader :name, :cells
     class Cell
         attr_reader :x, :y, :position, :playerId
         attr_writer :x, :y, :position, :playerId
         def initialize(x, y, position)
             @x = x
             @y = y
             @playerId = 0
             @position = position
         end

         def to_s
             puts "(#@x, #@y): #@position, #@playerId"
         end
     end

     def loadDefaultTactic
  file = File.new('tactics.dat')
  # Identificador de la tactica
  @name = file.readline
  # Posiciones
  file.each(';') {
      >line> coords = line.split(',')
      x, y = coords[0].to_i, coords[1].to_i
      @cells << Cell.new(x, y, getPosition(x, y))
  }
  file.close
     end

     def initialize
         @cells = Array.new
         # TODO Hay que leer el fichero de datos y cargar la tactica por defecto
     end

     def to_s
  puts "#@name"
     end
end

I do:

tactic = Tactic.new
tactic.loadDefaultTactic
puts tactic

and get:

4-4-2
#<Tactic:0xb78db8fc>

Why do I get the internal representation of Tactic?

Why is not the response '4-4-2' only?

4-4-2

(James Edward Gray II) #2

Hi all, I have this class:

class Tactic

# ...

        def to_s
            puts "(#@x, #@y): #@position, #@playerId"
        end

# ...

    def to_s
    puts "#@name"
    end
end

The above methods should not be calling puts(). They just need to return a String.

Hope that helps.

James Edward Gray II

···

On Aug 16, 2005, at 8:36 AM, EdUarDo wrote:

(Gavin Kistner) #3

Change that to:
def to_s
     "#@name"
end

The #to_s method should return the string representation, not output it.

···

On Aug 16, 2005, at 7:36 AM, EdUarDo wrote:

    def to_s
    puts "#@name"
    end

(Robert) #4

EdUarDo wrote:

Hi all, I have this class:

class Tactic
     attr_reader :name, :cells
     class Cell
         attr_reader :x, :y, :position, :playerId
         attr_writer :x, :y, :position, :playerId
         def initialize(x, y, position)
             @x = x
             @y = y
             @playerId = 0
             @position = position
         end

         def to_s
             puts "(#@x, #@y): #@position, #@playerId"
         end
     end

     def loadDefaultTactic
file = File.new('tactics.dat')
# Identificador de la tactica
@name = file.readline
# Posiciones
file.each(';') {
    >line> coords = line.split(',')
    x, y = coords[0].to_i, coords[1].to_i
    @cells << Cell.new(x, y, getPosition(x, y))
}
file.close
     end

     def initialize
         @cells = Array.new
         # TODO Hay que leer el fichero de datos y cargar la tactica
     por defecto end

     def to_s
puts "#@name"
     end
end

I do:

tactic = Tactic.new
tactic.loadDefaultTactic
puts tactic

and get:

4-4-2
#<Tactic:0xb78db8fc>

Why do I get the internal representation of Tactic?

Because your to_s method returns nil. You want this

def to_s() @name.to_s end

and not

def to_s() puts "#@name" end

Why is not the response '4-4-2' only?

Maybe you have an error in the reading code (file.each for example).

I'd also use the block form:

File.open('tactics.dat') do |file|
  # read
end

Kind regards

    robert

(Nobuyoshi Nakada) #5

Hi,

At Tue, 16 Aug 2005 22:36:14 +0900,
EdUarDo wrote in [ruby-talk:152360]:

     def to_s
  puts "#@name"
     end

You don't return a String, but nil.

Why do I get the internal representation of Tactic?

`puts' converts the arguments by calling `to_s', but use
default `to_s' if it didn't return a String.

···

--
Nobu Nakada

(Charles Steinman) #6

EdUarDo wrote:

     def to_s
  puts "#@name"
     end
end

I do:

tactic = Tactic.new
tactic.loadDefaultTactic
puts tactic

and get:

4-4-2
#<Tactic:0xb78db8fc>

Why do I get the internal representation of Tactic?

Why is not the response '4-4-2' only?

You are not returning "4-4-2" in to_s. You are directly printing
"4-4-2" with puts in the to_s method. The return value of puts is nil.
So to_s is printing "4-4-2" and then returning nil. And when to_s
returns nil, puts will instead use inspect to get a string for output.
So the second puts prints tactic.inspect.

You want your to_s method to look something like this:

def to_s
  @name.to_s
end

(EdUarDo) #7

Ok, ok, I think I'll never forget!! :), thanks for the answers to all

(EdUarDo) #8

Because your to_s method returns nil. You want this

def to_s() @name.to_s end

and not

That's right, I forgot that to_s must return a string, not to print a string

I'd also use the block form:

File.open('tactics.dat') do |file|
  # read
end

I'll do, thanks a lot.