Tech Racho エンジニアの「?」を「!」に。
  • Ruby / Rails関連

Ruby の'include?'より Rails の'in?`の方が読みやすい(翻訳)

概要

元サイトの許諾を得て翻訳・公開いたします。

日本語タイトルは内容に即したものにしました。

Ruby の'include?'より Rails の'in?'の方が読みやすい(翻訳)

Rubyでコレクションに値が存在するかどうかのチェックにはRubyのinclude?が使えますが、RailsのActive Supportが提供しているin?メソッドなら同じことをもっと自然に書けます。

🔗 以下のように書くよりも

include?を使う(コレクション.include?(チェック対象)の順序になる)。

nsync = ["Justin", "JC", "Chris", "Joey", "Lance"]

if nsync.include?(candidate)
  puts "#{candidate} is in the band"
end

# インラインで書く場合
if ["Justin", "JC", "Chris", "Joey", "Lance"].include?(member)
  puts "#{member} can join the inevitable reunion tour"
end

🔗 以下のように書こう

Railsのin?メソッドを使う(チェック対象.in?(コレクション)のように英語的に自然に読める)。

nsync = ["Justin", "JC", "Chris", "Joey", "Lance"]

if candidate.in?(nsync)
  puts "#{candidate} is in the band"
end

# インラインで書くとさらに自然
if member.in?(["Justin", "JC", "Chris", "Joey", "Lance"])
  puts "#{member} can join the inevitable reunion tour"
end

🔗 そうする理由

in?メソッドを使うと、"Is Justin in NSYNC?"という英文がそのまま"Justin".in?(nsync)と書けるようになります。

逆にnsync.include?("Justin")を英文的に読むと"Does NSYNC include Justin?"となります。別に文法的に間違ってはいないのですが少々直感に反しています。

Railsのin?メソッドは、include?に応答するオブジェクト(Array、Range、Set、String)であればどれにでも使えます。

"JC".in?("JC Chasez")                            #=> true
5.in?(1..10)                                     #=> true
:harmony.in?(Set[:melody, :harmony, :rhythm])    #=> true

in?メソッドならチェック対象がnilの場合にもエラーではなくfalseを返してくれます。

"Justin".in?(nil)  #=> false

🔗 そうしない理由があるとすれば

Railsを使っていないのであれば、依存関係としてGemfileにactivesupportを追加する必要があります。1個のメソッドのためにそこまでするのはオーバーキルかもしれません。

開発チームによっては、Railsの規約にあまり馴染みのない開発者を不必要に混乱させないために、こうした「マジック」メソッドを避けることもあるでしょう。コレクションの変数名が既に十分わかりやすければ、nsync.include?(name)のような書き方でも構いません。

in?はコレクションでinclude?を呼び出しているだけなので、パフォーマンスにも違いはありません。文脈に合っていれば、どちらを使っても構いません。

もっともインラインのコレクションに対して実行する場合や、条件文のコレクションよりも主語の方が重要である場合は、in?に軍配が上がります

関連記事

Rails の try メソッドと Ruby のぼっち演算子 '&.' の違いを理解する(翻訳)

Rails: Active Supportのdeep_dupの適切な使い所を理解する(翻訳)

Railsのblank?やpresent?は積極的に使おう(翻訳)


CONTACT

TechRachoでは、パートナーシップをご検討いただける方からの
ご連絡をお待ちしております。ぜひお気軽にご意見・ご相談ください。