In this article, we’re going to explore the following topics:

the attr method

method the attr_reader method

method the attr_writer method

method the attr_accessor method

method lazy initialization

Before to start

I’m thrilled to share with you our latest project: Fun Facts about Ruby — Volume 1

Please feel free to spread the word and share this post! 🙏

Thank you for your time!

Introduction

In OOP, the member access control concept is important as it allows to control the access to encapsulated variables.

In many programming languages, this concept is implemented by using getters and setters for each member.

In Ruby, the attr_* methods are in charge of the member access control .

attr

The attr method creates an instance variable and a getter method for each attribute name passed as argument.

An argument can be a Symbol or a String that will be converted to Symbol

module Attr

attr :attr1, 'attr2'

end irb> Attr.instance_methods

=> [:attr1, :attr2]

In the above example, the Attr module includes 2 instance methods that allow to read the value of attr1 and attr2 .

attr_reader

The attr_reader method is similar to the attr one

module Attr

attr_reader :attr1, 'attr2'

end irb> Attr.instance_methods

=> [:attr1, :attr2]

attr_writer

The attr_writer method creates an instance variable and a setter method for each attribute name passed as argument.

An argument can be a Symbol or a String that will be converted to Symbol

module Attr

attr_writer :attr1, 'attr2'

end irb> Attr.instance_methods

=> [:attr1=, :attr2=]

In the above example, the Attr module includes 2 instance methods that allow to modify the value of attr1 and attr2 .

attr_accessor

The attr_accessor method creates an instance variable, a getter and a setter method for each attribute name passed as argument.

An argument can be a Symbol or a String that will be converted to Symbol

module Attr

attr_accessor :attr1, 'attr2'

end irb> Attr.instance_methods.sort

=> [:attr1, :attr1=, :attr2, :attr2=]

In the above example, the Attr module includes 4 instance methods that allow to read and modify the value of attr1 and attr2 .

Lazy Initialization

In the previous examples, I told you that the attr_* methods create instance variables. It’s almost true.

In effect, the instance variables created by the attr_* methods use the lazy initialization mechanism.

This means that the instance variables are only initialized when the setter method is invoked — or when the instance variable is explicitly set within an instance method

class Website

attr_accessor :link, :title def initialize

@title = "The best Ruby newsletter"

end

end irb> website = Website.new

=> #<Website:0x00777 @title="The best Ruby newsletter">

irb> website.instance_variables

=> [:@title]

irb> website.link = "http://ruby.devscoop.fr"

=> "http://ruby.devscoop.fr"

irb> website.instance_variables

[:@title, :@link]

In the above example, the @title instance variable is explicitly created in the Website#initialize method.

So, this instance variable is available in the array returned by the first call to instance_variables .

Notice that the @link instance variable is not yet created, despite the call to attr_accessor . This instance variable is only created after the call to the Website#link= method.

So, by using the attr_* methods, the instance variable associated to each argument name will only be created when we set a value to it (by using the setter method or by explicitly assign a value to it).

Voilà !

May I have your attention please 🎤🎤

Feel free to subscribe here: www.rubycademy.com