画面出力
puts 改行、print 改行なし
gets 入力
p はputs 変数.inspectと同じ
変数
ローカル変数
注意、変数のスコープは上位のスコープを探さない。
ブロック、メソッド、クラス/モジュール定義の終わりまで。
class Hoge
x = “bye”
def initialize
x = “hello”
puts x
end
end
h = Hoge.new #=> hello
インスタンス変数
class User
def say
puts @x
@x = “b”
puts @x
end
def self.say2
puts @x
@x = “a”
puts @x
end
end
User::say2
#=> 空白
#=> a
u = User.new
u.say
#=> 空白
#=> b
@を前置する
インスタンス生成時に作られない。値の代入時に実体が生成される。
クラス定義内で定義しない。
通常メソッド内で定義するがスコープはクラス内となる。
(ローカル変数の場合メソッド内だけになってしまう。)
使えるのはinitializeメソッドとインスタンスメソッドのみ
@前置きの変数をクラスメソッド内で操作してもインスタンス側に変更はない。
クラスメソッド内での@前置きの変数はクラスインスタンス変数として動作している模様。
クラス変数
class User
@@x = “hello”
def say
puts @@x
end
def self.say2
puts @@x
end
end
User::say2 #=> hello
u = User.new
u.say #=> hello
@@を前置して、クラス定義の中に書く。
クラスメソッド、インスタンスメソッド、クラス定義式内でアクセス可能
クラスインスタンス変数
class User
@x = “hello”
def say
puts @x
end
def self.say2
puts @x
end
end
User::say2 #=> hello
u = User.new
u.say #=> 空白
作り方は、@を前置きするのはインスタンス変数と一緒で、クラス定義内で定義するだけ。
機能はほぼクラス変数。違いはインスタンスメソッドからアクセスすることはできない
クラス・インスタンス変数のまとめ
@も@@もクラス内スコープ
ただ、@@はクラスで既に実体があるが、
@はインスタンス生成後、さらに代入などの処理があって実体ができる。
例えば、
class User
@x = “hello”
def say
puts @x
end
end
u = User.new
u.say
これでは空白が出力
@xを@@xにすればhelloが出力される。
class User
@@x = “hello”
def self.fst
@@x = “bye”
end
def say
puts @@x
end
end
User::fst
u = User.new
u.say #=> bye
クラス変数は実体がクラスにあるので、クラスメソッドでの変更後
インスタンスを生成すると変更の影響を受けている。
つまり、@も@@もスコープはクラスの変数。
@をクラスで定義したりクラスメソッドで定義すると、クラス変数と同様のクラスインスタンス変数になるが、
値を入れておいてもインスタンス生成時に値が破棄される。
(インスタンスでの@とクラスにある@が別のスコープの別変数として存在している)
継承についても注意が必要で、@@は継承後も値は破棄されないが、
@は継承時にインスタンス生成と同じように破棄される。
@も@@も共にスコープはクラスなので、@をクラス変数の様に使うことも可能だが、
そうすると、インスタンスや継承時の動作に注意が必要。
class User
@x = “hello”
def self.fst
puts @x
@x = “bye”
puts @x
end
def say
puts @x
end
end
User::fst
u = User.new
u.say
#=> hello
#=> bye
#=> 空白
@変数をクラス変数の代わりに利用。インスタンスで使わないなら問題ない。
グローバル変数
$を前置
スコープ無視
モジュール
module Hoge
x = “hello”
def self.say
x = “bye”
puts x
end
def sayHello
puts “Hello Hello”
end
end
Hoge::say #=> bye
ここのxはローカル変数であって、スコープ外なのでx=byeがないとエラー
class HogeHoge
include Hoge
end
HogeHoge::say
モジュールでのクラスメソッドはインクルードされない。
h = HogeHoge.new
h.say #=> NG
h.sayHello #=> Hello Hello
モジュールのクラスメソッドはインクルードされない。
インクルードされるのはインスタンスメソッドのみ
module Fuga
@x = “hey”
def self.say
puts @x
end
end
Fuga::say #=> hello
class FugaFuga
include Fuga
def say
puts @x
end
end
f = FugaFuga.new
f.say #=> 空白
Fugaでの変数が@@xならheyと表示される
ミックスインでも@@はインクルードされるけど、@は破棄されるということ。
演算子
=== は、ほとんど == と同じだけど、
正規表現 === 変数 だとマッチするかどうか、
クラス === 変数 だとそのクラスのオブジェクトかどうか判断する。
型
数値
Fixnum
Bignum
Float
型はないので自由な値が入る。入っている値によって
指し示すオブジェクトが変わる。
型の自動変換はないので、
to_s
to_f
to_i
文字列
連結は+
“”は式展開あり #{ xxx }
”は式展開なし
囲う
%q = ‘xxx’と同じ
%Q = “xxx”と同じ
% = “xxx”と同じ
%r{xxx} = /xxx/と同じ(正規表現)
%w(xxx,xxx,xxx) は配列(Wだと式展開あり)
配列
[“dog”,”cat”]
include?
length
empty?
などのメソッドがある。
追加は <<
要素を超えて、取り出すとnil、加えると自動で大きくなる。
オブジェクトなら何でもはいる。
条件分岐
0,や空文字もtrueになる。falseはnilとfalseだけ。
比較演算子はtrue/falseを返す b = (a == c)等
条件分岐に入ると、真偽問わず、スコープの中にある変数は初期化される。
スコープ
if,for,while,case
などの条件式で、スコープを作らない。
メソッド、ブロックではスコープができる。
x = “hello”
def fnc
x = “bye”
puts x
end
puts x
fnc
#=> hello
#=> bye
面白いのは、インスタンス変数でも同じということ
これは既にmainというクラスの中にいるから。
@x = “hello”
def fnc
@x = “bye”
puts @x
end
puts @x
fnc
#=> hello
#=> bye
クラスで囲うとどうなるか。
class User
@x = “hello” #<1>
def fnc
@x = “bye”
puts @x
end
puts @x #<2>
end
u = User.new
u.fnc
#=> hello
#=> bye
この結果も同じだけど、これはインスタンス生成時に、classが評価されて、
最初のhelloが出力されている。実際、u.fncを呼ばなくてもhelloは出力されるし、
<1><2>のどちらかを消すとhelloを出力されない。
そのあとのbyeは普通どおりインスタンスからfncを呼んでいるから出力される。
インスタンス生成後も@x = “hello”は生きているけど、それはクラスのスコープであって
インスタンスには存在しない。
class User
def fnc
@x = “b”
puts @x
end
def fnc2
puts @x
end
end
u = User.new
u.fnc
u.fnc2
#=> b
#=> b
インスタンス変数はクラススコープなので、最初fncでbが入り、次のfnc2でもその値が生きている。
fncをせずにfnc2を呼ぶと空白が出力される。
メソッド
途中で抜ける場合 returnも使える。
初期値を指定できる
def xx(var = “hello”)
end
引数の数量不定にすると配列になる
def fuc(*var)
end
第1引数はfstに入り、それ以降がvarの配列へ
def fuc(fst, *var)
end
名称について
? = true/falseを返す
! = 破壊的メソッド
ブロック
メソッド呼び出し時に定義する。メソッドに渡す処理の塊。
渡したメソッド内ではなく、ブロックを定義したスコープにいる。
yieldでメソッド側からブロックに引数を渡せる。
例外処理
begin
rescue
例外時
else
例外がない場合
end
メソッドなら
def
rescue
例外時
else
例外がない場合
end
とも書ける。
rescue => 変数で取り出す。
ハッシュ
population = {“France”=>100}
puts population [“France”]
キーがシンボルなら、以下の書き方ができる。
pop = {:fr => 100 }
なら、
pop = { fr:100 }
とできる。(スペースはいれない)
取り出すときは
pop [:fr]
となる。
範囲
1..10 # 1から10まで
1…10 # 1から9まで
正規表現
=~ で比較できる。
!~ は逆
string.gsubで置き換え。
日付
日時はTimeクラス
Dateオブジェクトは日付だけを扱う
日時の取り出し
t = Time.now
t.year
t.month
t.day
t.hour
t.min
t.sec
作る時
Time.local(2015,12,31,23,59,59)
整形はstrftime
t = Time.now
t.strftime(“%Y/%m/%d %H:%M”)
参照渡し
参照の値渡しになっている。
str1 = “hello”
str2 = “goodbye”
print “str1=”, str1.object_id, “\n”
print “str2=”, str2.object_id, “\n”
str1 = str2 #ここでstr1もstr2も”goodbye”を指している
str1.upcase!
print “str1=”, str1.object_id, “\n”
print “str2=”, str2.object_id, “\n”
puts str1,str2
str1=71129430
str2=71129420
str1=71129420
str2=71129420
GOODBYE
GOODBYE
クラスとメソッドについて
ドット記法はメソッド呼び出し
レシーバ.メソッド
二重コロンは
定数呼び出し、メソッドも呼べる。
rubyのインスタンスの内部的にはインスタンス変数とメソッドへのリンクだけ。
メソッドの定義はクラスに持っている。
ただ、通常のメソッド定義だとインスタンスに紐付いてクラスから直接呼べない
インスタンスメソッドをクラスから呼ぶNG
class Hoge
def piyo
”hoge”
end
end
p Hoge.piyo #=> undefined method
インスタンスメソッドをインスタンスから呼ぶOK
class Hoge
def piyo
”hoge”
end
end
h = Hoge.new
p h.piyo #=> hoge
クラスメソッドをクラスから呼ぶOK
class Hoge
def self.piyo
”hoge”
end
end
p Hoge.piyo #=> hoge
クラスメソッドをインスタンスから呼ぶNG
class Hoge
def self.piyo
”hoge”
end
end
h = Hoge.new
p h.piyo
と分けられる。
アクセサメソッド
自動で生成したい場合、インスタンス変数の名前をシンボルで渡す。
attr_accessor :name
そうすると、以下の2つのメソッドを自動で作る。
name=(value) # setter
name # getter
実体は以下のような感じ
class User
def name
@name
end
def name=(name)
@name = name
end
end
それぞれ1つだけでいい場合。
attr_reader :name
attr_writer :name
クラス内でアクセッサメソッドを呼ぶ時、
レシーバを省略して呼ぶと、ローカル変数とみなされてしまうので注意
メソッドのアクセス範囲
public
どこからでも
private
同クラス、サブクラスから読める。
レシーバ付けられない。関数形式でしか呼び出せない。
protected
同クラス、サブクラスから読める
レシーバ付けられる。
そのメソッドを持つオブジェクトがselfの場所でのみ呼び出せる