About instance variables and attr_ *

Overview

Even if it is a convenient function, there may be some disadvantages.

Therefore, the user needs to be able to judge the balance between advantages and disadvantages and implement it appropriately. I thought, I summarized it in an article.

In some cases, the difficulty of maintenance actually outweighs the difficulty, and is it necessary again? I hope it will be helpful for you to consider

What happens if you use attr_ * first?

ʻAttr_reader: name` defines the getter method with the name of the argument

def name
  @name
end

ʻAttr_writer: name` defines the setter method with the name of the argument

def name=(val)
  @name = val
end

ʻAttr_accessor: name` is a composite method of reader and writer

Normally, instance variables that can be accessed by @hoge inside the instance are defined by public methods, so the value of the instance variable can be touched from the outside.

At this time, it is also possible to define the method privately by using private.

private
attr_reader :hoge

About advantages and disadvantages

merit

Call from the outside

It can be used from the outside because it is cut as the public method, which is the original purpose.

As you all know here.

Ease of repair

class Hoge
  private
  attr_accessor :hoge

  def initialize(hoge:)
    @hoge = hoge
  end

  def connect
    Service.call(hoge: hoge) # <-Here
  end
end

When it's implemented like this

def hoge
  @hoge + 1
end

If you need to fix it like this, you can override it to make it easier to fix.

Demerit

Scope awareness

You need to think correctly about public or private, etc.

Method definition

Inadvertent method definition can lead to method name conflicts

readability

--If you can override it, is the method overridden? Need to check => Readability is reduced

Example

class Hoge
  include Hoge::XXXable
  include Hoge::ZZZable

  private
  attr_accessor :hoge

  def initialize(hoge:)
    @hoge = hoge
  end

  def connect
    Service.call(param: param)
  end
end

module Hoge::XXXable
  include ::YYYable
  def param
    {
      hoge: hoge # <-Here
    }
  end
end

For the prerequisite module (cutout module) included in the target class in this way It just references an instance variable but can be a method call

This is

module Hoge::XXXable
  include ::YYYable
  def param
    {
      hoge: @hoge # <-Here
    }
  end
end

If it is, you can easily understand that "the instance variable of the class to be included and loaded is set" just by looking at the source in the module.

However, since this is an attr getter method, if you just look at the XXXable module, where is the hoge defined? I don't understand. So somewhere below? The work of searching for will occur. --Is it defined in XXXable? --In the module included or extended by XXXable --Classes and modules that include XXXable --The module loaded by the class or module that includes XXXable

Conclusion

** Easy to maintain ** mentioned in the merit is applicable in the sense that it is easy to overwrite. If the need is unpredictable at this stage, isn't it ** difficult to maintain **?

Isn't this a case where these disadvantages become greater when using it? I will consider whether to use it while thinking again I would like to write a better program

Recommended Posts

About instance variables and attr_ *
Difference between variables and instance variables
Organize classes, instances, and instance variables
[Java] Differences between instance variables and class variables
About Enclosing Instance 2
Find out about instance methods and self
Ruby: Differences between class methods and instance methods, class variables and instance variables
About Bean and DI
About classes and instances
About gets and gets.chomp
About calling instance methods
About redirect and forward
[Swift] Constants and variables
About encapsulation and inheritance
Ruby variables and methods
[Ruby] About instance generation
About Serializable and serialVersionUID
[Java] Variables and types
[Java Silver] What are class variables instance variables and local variables?
About for statement and if statement
About an instance of java
About synchronized and Reentrant Lock
Java programming (variables and data)
About Ruby hashes and symbols
[Java] About String and StringBuilder
About the same and equivalent
Difference between class and instance
About classes and instances (evolution)
About pluck and ids methods
Consideration about classes and instances
About Java class variables class methods
About Java Packages and imports
About Ruby and object model
[Programming Complete] §4 Variables and constants
Ruby variables and functions (methods)
About self-introduction and common errors
[Ruby] Difference between symbol variables and character string variables. About the difference between [: a] and ['a'].
About the range and scope where Day16 variables can be used
Difference between instance method and class method
About C # lambda expressions and Linq
About Java static and non-static methods
About fastqc of Biocontainers and Java
Find out about environment variables (memo)
Java Primer Series (Variables and Types)
About the equals () and hashcode () methods
[Java beginner] About abstraction and interface
About Ruby single quotes and double quotes
[Ruby] Classes, instance variables, instances, etc ...
About Gradle's setup phase and execution phase
Difference between instance variable and class variable
About Ruby product operator (&) and sum operator (|)
[Ruby] Handle instance variables with instance methods
About removeAll and retainAll of ArrayList
About if statement and branch processing
About object-oriented inheritance and about yield Ruby
About Java primitive types and reference types
Consideration about Rails and Clean Architecture
This and that about Base64 (Java)
About Docker, disguise server and container