Logicky Blog

Logickyの開発ブログです

Rubyのempty, false, nilなど

empty, false, nilとrailsにはblankもあるらしいけど、これしっかり覚える。

nil? empty? blank? present? の使い分け

nil? すべてのオブジェクトに定義されている。nilのときのみtrueを返す。 empty? 文字列の長さが0のとき、または配列が空のときにTrueを返す。もちろん数値には定義されていない。 blank? railsの拡張。nil, "", " ", [], {} のいずれかでTrueを返す。 present?は、!blank?と同じ意味

結果

・0 false nilは別物 ・nil?は、nilのときtrue。 (未定義の変数に使うとエラーになる。存在する配列の中の、存在しない要素だとエラーにならず、trueを返す) ・empty?は、文字列、配列に使えて、空文字列か配列が空のときtrue ・blank?は、nil, false, 空文字列, スペースだけの文字列, 配列が空のときtrue  (未定義の変数に使うとエラーになる。存在する配列の中の、存在しない要素だとエラーにならず、trueを返す) ・present?は、!blank? PHPよりわかり易いと思った。 ・変数が定義済みかを確認するには、defined?を使える。

irbでやってみる。

a = 1
a.nil?
false
a.empty?
ERROR
a.blank?
ERROR
a.present?
ERROR

b = ''
b.nil?
false
b.empty?
true
b.blank?
ERROR
b.present?
ERROR

c = false
c.nil?
false
c.empty?
ERROR

d = 0
d.nil?
false
d.empty?
ERROR

z.nil?
ERROR

定義してない変数にnil使ってもエラー。falseでも0でも定義さえしてたら、nilじゃない。

c == 0
false

falseは0でもnilでもない。

f = []
f.length
0
f.empty?
true
f.nil?
false

emptyは文字列、配列に使える。数値には使えない。

rails consoleでやってみる。

$ rails c
a = 1
a.empty?
ERROR
a.blank?
false
a.present?
true

b = 0
b.empty?
ERROR
b.blank?
false
b.present?
true

c = ''
c.empty?
true
c.blank?
true
c.present?
false

d = false
d.empty?
ERROR
d.blank?
true
d.present?
false

falseの場合もblank?はtrueを返す。

e = {}
e.empty?
true
e.blank?
true
e.present?
false

f(未定義)
ERROR
f.empty?
ERROR
f.blank?
ERROR
f.present?
ERROR

あら未定義だとblankもpresentもエラーになる。 railsのコントローラ上で試してみてもエラーになった。 定義済みじゃないとエラーになるのか。色々PHPと違う。

a = false
logger.debug 'a is blank' if a.blank?
# logger.debug a if b.blank?
c = {'a': 12, 'b':13}
logger.debug 'c[:a] is present' if c[:a].present?
logger.debug 'c[:c] is blank' if c[:c].blank?
d = '    '
e = '   '
logger.debug 'd is blank' if d.blank?
logger.debug 'e is blank' if e.blank?
logger.debug 'c[:c] is nil' if c[:c].nil?

上記をコントローラでやると、development.logに下記が表示される。

a is blank
c[:a] is present
c[:c] is blank
d is blank
e is blank
c[:c] is nil

配列の要素に対しては、blankを使ってもエラーにならないらしい。

また、rails consoleでやってみる。

c = {}
c['a'].blank?
true
c['a'].empty?
ERROR
c[:a].nil?
true

あとは一応クラスつくって試してみる。

class Hoge
  attr_accessor :name
end
a = Hoge.new
a.name
nil
a.name.nil?
true
a.name.empty?
ERROR
Hoge.nil?
false
Hoge.blank?
false
Hoge.present?
true
a.nil?
false
a.blank?
false
a.present?
true

変数が存在するか確認するには、definedが使えるらしい。

rails consoleで試してみる

a = false
b = ''
c = []
d = new Hoge

defined? a
=> "local-variable"
defined? b
=> "local-variable"
defined? c
=> "local-variable"
defined? d
=> "local-variable"
defined? c[:a]
=> "method"
defined? d.name
=> "method"
defined? d.hoge
=> nil
defined? z
=> nil

未定義の変数に使ったらnilが返ってくる。存在する配列の存在しない要素に使うと、methodって返ってくる。存在するオブジェクトの値がnilのメンバ変数に使うと、methodって返ってくる。