クラス
オリジナルのクラスを作成する例:箱を定義するクラス
Boxクラス
メソッド hello ・・・ helloと出力する機能
class Box def hello puts 'hello' end end box = Box.new box.hello hello
class Box def initialize(name) puts 'initialize' @name = name #インスタンス変数はインスタンス内であればどこでも使える #↑逆にこれは他では使えない end def hello puts "Hello! I am #{@name}." end end box = Box.new('Cardboard') box.hello wood = Box.new('wood') wood.hello #.rbで出力すると initialize Hello! I am wood.
更にインスタンスを追加することもできる
class Box def initialize(name) puts 'initialize' @name = name end def hello puts "Hello! I am #{@name}." end end box = Box.new('Cardboard') box.hello wood = Box.new('wood') wood.hello #.rbで出力すると initialize Hello! I am Cardboard. initialize Hello! I am wood.
アクセサメソッド:インスタンス変数の値を読み書きするメソッドのこと
class Box def initialize(name) @name = name end def hello puts "Hello! I am #{@name}." end def name @name end end box = Box.new('Cardboard') puts box.name #.rbで出力すると initialize hello! I am Cardboard. Cardboard
クラスの外からnameメソッドでインスタンス変数を呼び出した
インスタンス変数の@nameの値をクラスの外から書き換えたい
class Box def initialize(name) @name = name end def hello puts "Hello! I am #{@name}." end def name @name end end box = Box.new('Cardboard') puts box.name #.rbで出力すると Cardboard box.@name = 'suzutuki' ↑Syntax error インスタンス変数は外から書き換えられない
ではどうするか?書き込み用のメソッドを作る
class Box def initialize(name) # puts 'initialize' @name = name end def hello puts "Hello! I am #{@name}." end #他の言語だとゲッターメソッド def name @name end #他の言語だとセッターメソッド def name=(value) #←ここから @name = value end end box = Box.new('Cardboard') # box.hello puts box.name box.name = 'suzutuki' puts box.name #.rbで出力すると Cardboard suzutuki name=のように=で終わるメソッドを定義すると 変数に代入するような形でメソッドが呼び出される。 box.name = 'suzutuki'という書き方ができるようになる メソッドを呼び出しているけれども 値('suzutuki')を代入するような書き方ができる。
インスタンス変数を読み書きするメソッドのことを
インスタンスメソッドと呼ぶ
設定を書き換えたいとき
アクセサメソッドattr_accessorメソッド
attrはattributeで属性のこと
インスタンスメソッドを開発者が書かなくて良くなる
class Box attr_accessor :name def initialize(name) puts 'initialize' @name = name end def hello puts "Hello! I am #{@name}." end # def name # @name # end # def name=(a) # @name = a # end end box = Box.new('Cardboard') puts box.name box.name = 'suzutuki' puts box.name ↓ruby accessor.rbで出力 Cardboard suzutuki class Box attr_accessor :name end box = Box.new puts box.name box.name = 'suzutuki' puts box.name #.rbで出力すると suzutuki ※空欄はnilで初期引数を指定しないとなる
コメントアウトしているところを1行で書くことができる
定型文的なメソッドを毎回書かなくて良いので開発を効率化できる
読み込みのみしたいとき
class Box attr_reader :name def initialize(name) @name = name end def hello puts "Hello! I am #{@name}." end # def name # @name # end # def name=(a) # @name = a # end end box = Box.new('Cardboard') # box.hello puts box.name # box.name = 'suzutuki'書き込みをしようとするとエラーになる puts box.name ↓ruby accessor.rb Cardboard Cardboard ↑書き込みがされてないので2回Cardboardが出力された なお書き込もうとするとエラーが出る↓ accessor.rb:26:in `<main>': undefined method `name=' for #<Box:0x00000000021c7df0 @name="Cardboard"> (NoMethodError) Did you mean? name
書き込みのみしたいとき
class Box attr_writer :name def initialize(name) @name = name end def hello puts "Hello! I am #{@name}." end # def name # @name # end # def name=(a) # @name = a # end end box = Box.new('Cardboard') # box.hello # puts box.name box.name = 'suzutuki' # puts box.name #.rbで出力すると 何も起きてないように見えるが書き込みはされている。表示はされない
クラス変数:クラス自体に値を保持できる変数
class Box @@count = 0 def initialize(name) @name = name @@count += 1 end def hello puts "Hello! I am #{@name}. #{@@count} instance(s)." end end kit = Box.new('Cardboard') kit.hello wood = Box.new('wood') wood.hello suzutuki = Box.new('suzutuki') suzutuki.hello #.rbで出力すると Hello! I am Cardboard. 1 instance(s). Hello! I am wood. 2 instance(s). Hello! I am suzutuki. 3 instance(s).
クラスメソッドinfoを定義、クラスメソッドinfoを実行すると
インスタンスの生成回数(@@count)を出力する
class Box @@count = 0 def initialize(name) @name = name @@count += 1 end def hello puts "Hello! I am #{@name}. #{@@count} instance(s)." end def self.info puts "#{@@count} instance(s)." end end Box.info #.rbで出力すると 0 instance(s). ↑インスタンスの生成が行われていないので0
class Box @@count = 0 def initialize(name) @name = name @@count += 1 end def hello puts "Hello! I am #{@name}. #{@@count} instance(s)." end def self.info puts "#{@@count} instance(s)." end end kit = Box.new('Cardboard') Box.info wood = Box.new('wood') Box.info suzutuki = Box.new('suzutuki') Box.info #.rbで出力すると 1 instance(s) 2 instance(s) 3 instance(s)
一つのクラス変数@@countをそれぞれのインスタンスが共通して
利用していることがわかる
class FF def self.first_method puts '1' end class << self def second_method puts '2' end def third_method puts '3' end end end FF.first_method FF.second_method FF.third_method #.rbで出力すると '1' '2' '3' FF.new.varだとエラー オブジェクトからクラスメソッドを呼び出そうとしてもエラーになる
クラスと定数
class Box REGION = 'USA' @@count = 0 def initialize(name) @name = name @@count += 1 end def hello puts "Hello! I am #{@name}. #{@@count} instance(s)." end def self.info puts "#{@@count} instance(s). Region: #{REGION}" end end kit = Box.new('Cardboard') Box.info wood = Box.new('wood') Box.info suzutuki = Box.new('suzutuki') Box.info puts Box::REGION クラスの外から呼び出せる #.rbで出力すると 1 instance(s). Region: USA 2 instance(s). Region: USA 3 instance(s). Region: USA ↓putsがあるので4番目のUSAも出力されている。ないと3行まで USA
クラスの継承
親クラスを作成することで親クラスの機能を引き継いで、
子クラスを作成することができる。
コードの再利用性や拡張性を高める仕組み
#親クラスのUserを作る class User def initialize(name) @name = name end def hello puts "Hello! I am #{@name}" end end akina = User.new('akina') akina.hello #.rbで出力すると Hello! I am akina
class AdminUser < User #子クラスまたはサブクラスを作った def hello_admin puts "Hello! I am #{@name} from AdminUser." end end suzutuki = AdminUser.new('suzutuki') suzutuki.hello suzutuki.hello_admin #.rbで出力すると Hello! I am akina Hello! I am suzutuki Hello! I am suzutuki from AdminUser.
class User def initialize(name) @name = name end def hello puts "Hello! I am #{@name}" end end #子クラスまたはサブクラスを作った class AdminUser < User def hello_admin puts "Hello! I am #{@name} from AdminUser." end #↓helloメソッドをAdminUserの方でオーバーライドする def hello puts 'Admin!!' end end suzutuki = AdminUser.new('suzutuki') suzutuki.hello suzutuki.hello_admin #.rbで出力すると Admin!! Hello! I am suzutuki from AdminUser.
親クラスから小クラスのメソッドは呼び出せないのに注意!
子クラスを編集することにより親クラスに変更を加えることなく
子クラスに機能を追加したり上書き(オーバーライド)することができる!
class User def initialize(name) @name = name end def hello puts "Hello! I am #{@name}" end end class AdminUser < User def hello_admin puts "Hello! I am #{@name} from AdminUser." end #↓helloメソッドをAdminUserの方でオーバーライドする def hello super puts 'Admin!!' end end suzutuki = AdminUser.new('suzutuki') suzutuki.hello akane = AdminUser.new('akane') akane.hello #.rbで出力すると Hello! I am suzutuki Admin!! Hello! I am akane Admin!! 親クラスのUserクラスのhelloも呼び出されている!
Integerの継承関係から継承関係を見ることができる
BasicObject ↑ Object ↑ Numeric ↑ Integer
#superclassで親クラスを知ることができる Integer.superclass => Numeric 2.5.1 :002 > Numeric.superclass => Object 2.5.1 :003 > Object.superclass => BasicObject 2.5.1 :004 > BasicObject.superclass => nil