0

Heey I am new to Ruby. I need to create a factory method, which will return me an object of a class. Using that object I should be able to access the variables of the class. I have written the following code, but I surely have miss something.

class Super
  @@super_temp = 1

  def Super.get_instance(world)          
    platform = world
    if @@instance == nil
      if platform==1
        @@instance = BaseA.new
      else
        @@instance = BaseB.new
      end
    end
    return @@instance
  end
end

class BaseA < Super    
  @@base_temp = 2      
end


class BaseB < Super
  @@base_temp = 3    
end


class Demo
  def Demo.call_demo
    obj = Super.get_instance(0)

    puts "---------temp is #{obj.base_temp}"      
  end
end

Demo.call_demo

I need to retrieve the value of base_temp in class Demo.

1
  • Why are you using class variables for this? In any case, class variables don't work like that--maybe check out some Ruby tutorials discussing the basics. Commented Jun 30, 2014 at 11:00

1 Answer 1

2

Don't use @@ (Why should we avoid using class variables @@ in rails?) - @ solves your problem just as easily.

Aside from that, all that is missing in your code is a getter:

class Super
  @super_temp = 1

  def Super.get_instance(world)          
    platform = world
    if @instance == nil
      if platform==1
        @instance = BaseA.new
      else
        @instance = BaseB.new
      end
    end
    return @instance
  end

  def base_temp
    self.class.base_temp
  end

  def self.base_temp
    @base_temp
  end
end

class BaseA < Super    
  @base_temp = 2      
end


class BaseB < Super
  @base_temp = 3    
end


class Demo
  def Demo.call_demo
    obj = Super.get_instance(0)

    puts "---------temp is #{obj.base_temp}"      
  end
end

Demo.call_demo
# ---------temp is 3

The instance getter (implemented as self.class.base_temp) calls the class method base_temp of the instance's class. If we add prints of the internal products of the function, you can have some insights about its internals:

class Super
  def base_temp
    p self
    p self.class
    p self.class.base_temp
  end
end

BaseA.new.base_temp
# #<BaseA:0x000000027df9e0>
# BaseA
# 2

BaseB.new.base_temp
# #<BaseB:0x000000027e38b0>
# BaseB
# 3
Sign up to request clarification or add additional context in comments.

6 Comments

Hey Uri.. I understand <def self.base_temp> is the getter method. Could you please explain how does < def base_temp self.class.base_temp> work. I do not completely understand the working of it. Also since I have many variables, creating those many setter getter methods, doesn't seem like the ideal solution.
Super.get_instance is valid Ruby code. However, as you suggested, we should use self.get_instance because small change in the class name, doesn't require change in the rest of the code.
@DarekNędza - of course you are right, I've not used this syntax, so I forgot that it is legitimate. In the name of minimal code change, I've removed that observation completely.
@UriAgassi The works fine. but I was just wondering, since I have many constant variables in my code. Do I have to write those setter, getter methods for each variable(which would be a major code block), or is there a way around?
@Hades - instance and class variables are private which means you can't [easily] access them outside the instance/class. You can implement getters as one liners (look for 'attr_reader')
|

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.