こんにちは! フリーエンジニアの長瀬です。今回取り上げるテーマは、Rubyでのattr_accesorの使い方です。
attr_accessorはゲッターとセッターを同時に定義することができる便利なものです。といっても、ゲッター?セッター?と何をいっているのかよくわからないと思いますので、段階を追って理解できるように工夫して記事を書きました。
この記事では、rubyのattr_accessorについてまずは
- クラスとは
- クラスのinitializeとは
- rubyの変数
- attr_reader(ゲッター)
- attr_writer(セッター)
- attr_accessor(ゲッターとセッターの両方)
といったように前半はrubyについての基本的な内容を、そして後半ではゲッターとセッターの定義方法についても解説していきます。
クラスについて
クラスとは
attr_accessorの使い方を理解するためには、まず「クラス」について知る必要があります。クラスを使えば、機能ごとにプログラムを整理することができます。プログラムの量が増えてくると、機能ごとに名前をつけた方が、明らかに整理しやすくなります。
ですが、プログラミングを始めたばかりの人はクラスの概念を理解するのが苦手です。というのも、初心者のうちは機能を分化の必要な量までのプログラミングをしたことがないからです。なので、その必要性をあまり感じることができないのです。
小規模のプログラムのうちは、そもそも機能を分化させて書く必要もないのですが、プログラムの量が増えてくるにつれて、機能をクラスとしてまとめていないと、ちょうど散らかった部屋のように整理ができていない状態になってしまいます。
そこで「クラス」というものを使うことで、その散らかった部屋を整理して、生産性の高いプログラミングをすることができるようになるのです。
記事の都合上、クラスについてはこれ以上説明しませんが、侍の他の記事にまとめられていますので、クラスについて理解が浅いと感じる方は一読することををおすすめします。
クラスのinitializeとは
クラスには、クラスの「初期設定」をするためのメソッドがあります。rubyの場合はinitializeが、その初期設定のためのメソッド名です。initialize内では、クラスで使用する変数を定義しておくことができます。
そして、その定義した変数はクラス内で使用することができます。initializeの使い方についてはこちらの記事にまとめられていますので、一読することをおすすめします。
rubyの変数
attr_accessorでは、「インスタンス変数」と呼ばれる変数を扱います。rubyには今回扱う「インスタンス変数」以外にもたくさんの変数があります。
ですので、「インスタンス変数」と言われてもいまいちピンとこない方は一度、変数についてのまとめ記事がございますので、こちらを一読することをおすすめします。
アクセサとは
Rubyではそのままだとインスタンス変数にアクセスできない仕様になっています。以下のコードをみてください。
class User @name = "" end user = User.new user.name = "taro" p user.name #=>rb:6:in `': undefined method `name=' for # (NoMethodError)
この定義の方法だと、@nameは「クラスインスタンス変数」と呼ばれる違う変数として定義され、インスタンスからはアクセスできない仕様になってしまいます。
ではインスタンスからアクセスすることのできるインスタンス変数はどのように定義すれば良いのでしょうか?
そのために存在するのがアクセサと呼ばれるものです!
アクセサメソッドの使い方
アクセサメソッドは次の2つがあります。
- attr_reader
- attr_writer
- attr_readerはインスタンス変数にアクセスするためのゲッター
- attr_writerはインスタンス変数にアクセスするこめのセッター
をそれぞれ定義します。
attr_reader(ゲッター)
class Human attr_reader :name def initialize(name) @name = name end end human = Human.new("taro") puts human.name
[実行結果]
taro
このように、attr_reader :nameと書くだけで、インスタンス変数@nameにアクセスできます。ですが、このままではセッターが定義されていないので、@nameをクラスの外部から変更することができません。
attr_writer(セッター)
class Human attr_writer :name attr_reader :name def initialize(name) @name = name end end human = Human.new("taro") puts human.name human.name = "siro" puts human.name
このように、attr_reader :nameに加えて、attr_writer :nameも書くことで、外部からインスタンス変数@nameを変更し、アクセスすることができます。
[実行結果]
taro siro
attr_accessor(ゲッターとセッターの両方)
確かに、attr_readerとattr_writerを使用すれば、ゲッターとセッターを定義できます。ですが、これら二つの機能を一つにまとめられたら便利だと思いませんか?
そこで用いられるのが「attr_accesor」メソッドです。書き方はとても簡単で、以下のように記述します。
attr_accesor :name
さきほどまでのサンプルコードを「attr_accesor」メソッドで書き直した場合は以下のようになります。
class Human attr_accessor :name def initialize(name) @name = name end end human = Human.new("taro") puts human.name human.name = "siro" puts human.name
[実行結果]
taro siro
短く、的確にコード処理ができていることが分かりますね。
まとめ
いかがでしたか。インスタンス変数へのアクセスに用いることができるアクセサメソッドについてわかっていただけましたか。
自作のゲッターやセッターを作成することもできますが、「attr_accesor」メソッドを用いることで簡単にゲッターとセッターを実装できます。
また、Railsでも、レコードに保存しない情報をモデルに紐付けて利用する際に使用します。RubyだけでなくRailsにも応用できるので覚えていて損はないでしょう。
関連記事