Rubyのチートシート / メソッドと例外処理

メソッドの基本的な書き方と例外処理。Railsチュートリアルを初めて読んだ時にcurrent_user=()みたいなメソッドがあって、え?てなったのを覚えてる…。

Rubyで使われる特殊な記号(!とか?とか)は下記サイトがとても参考になります。

Rubyで使われる記号の意味
Ruby QuickRef

 



# ---------------------------------------------- #
# メソッド
# ---------------------------------------------- #

puts "\n\n############## Option Hash ##############\n\n"

# **BAD***
# 引数が何個必要なのか、どの場所にどの引数なのか混乱しやすい
# デフォルト値が設定されていない引数を渡し忘れるとエラーになる
def get_profile_bad(user_id, name, email, age = 0, gender = 'femal')
    puts user_id
    puts name
    puts email
    puts age
    puts gender
end

# **GOOD**
# 必須でない引数はハッシュで受け取るとスッキリ
# user_id以外の引数はオプションなので渡さなくてもエラーにはならない
def set_profile_good(user_id, options = {})
    puts "ID   : #{user_id}"
    puts "NAME : #{options[:name]}"
    puts "MAIL : #{options[:email]}"
    puts "AGE  : #{options[:age]}"
    puts "GEN  : #{options[:gender]}"
end


# 実行する時は改行して見やすく

puts "\n--- GOOD ---\n\n"

set_profile_good(14,
        name:   "my name here",
        email:  "email@email.com",
        age:    99,
        gender: "male"
)


# 結果は同じだけど読みづらい

puts "\n--- BAD ---\n\n"

set_profile_good(14, {name: "my name here", email: "email@email.com", age: 99, gender: "male"})


# optionsを渡さなくても実行可能

puts "\n--- options省略 ---\n\n"

set_profile_good(14)





puts "\n\n############## 特殊な記号 ##############\n\n"


# "*"がついた引数で、それ以降の引数を配列として受け取る
# ---------------------------------------------- #
puts "--- Splat Arguments ---\n\n"

def show_names(status, *names)
    puts "STATUS : #{status}\nNAME   : #{names.join(', ')}"
end

# "fine"以外はnamesに配列として格納される
show_names("fine", "sawada", "sakata", "suzuki", "saito")



# '!'や'?'と同じく,'='も特別な意味を持っているが強制するものではない
# '='は代入するという意味をもったメソッド
# ---------------------------------------------- #

puts "\n--- 'xx=' method  ---\n\n"

class User

    def initialize(name)
        @name = name
    end

    ### アクセサメソッドを自分で定義 ###
    def name=(name)
        @name = name
    end

    def name
        @name
    end

    # xx=は単にメソッドなので、
    # @testインスタンス変数がなくても定義はできる
    def test=(text)
        puts text
    end

    ### アクセサメソッドは簡単に書ける ###

    # attr_accessor :name とすればメソッドを用意しなくても
    # インスタンス変数の中身を読んだり、変更したりできるので
    # name=(name)とnameメソッドは不要

    #attr_accessor :name
    #attr_reader: :name
    #attr_writer: :name

end

user = User.new("sawada")


#nameメソッド / 単にインスタンス変数@nameを返すだけ
puts user.name

# name=()メソッド
# インスタンスメソッドだからuserから呼び出せるのは当然
user.name=("kato")
puts user.name

# ()は省略できるけど、普通はこんな書き方はしない
user.name="suzuki"
puts user.name

# xx=タイプの名前のメソッドを定義すると、同時に「=」演算子を定義することになるので
# 下のような定番の書き方で、値をインスタンス変数に代入することができる
user.name = "saito"
puts user.name

# まず書かないと思うけど
# こんな代入っぽい書き方でも普通のメソッドのように振る舞う…
user.test = "テストだよ"






puts "\n\n############## 例外処理 ##############\n\n"

# 外部のAPIがダウンしてたりとか予想できないことも起こりうるので
# そんな時にアプリの処理を止めないよう例外処理がかける
# ---------------------------------------------- #

def find_from_api(name)

    users = ["sawada", "sakata", "suzuki", "saito"]

    if users.find { |u| u == name }
        puts "We found #{name} in users!\n"
    else
        raise StandardError.new("Hey! We got an error.\n")
    end
end


puts "--- 基本 ---\n\n"

begin
    find_from_api("batman")
rescue => e
    puts "Not found. #{e.message}" #エラーオブジェクトを受け取って表示
ensure
    find_from_api("sawada") #例外が発生しても行う処理
end


puts "\n--- 数回トライ ---\n\n"

error_count = 0
begin
    finding_from_api("sawada") #存在しないメソッド
rescue => e
    error_count += 1
    if error_count < 4
        puts "#{error_count}回目のエラーだよ…"
        puts "#{e.message}"
        retry
    end
ensure
    puts "あきらめた!"
end

上のコードを実行するとこうなるはずです。


############## Option Hash ##############


--- GOOD ---

ID   : 14
NAME : my name here
MAIL : email@email.com
AGE  : 99
GEN  : male

--- BAD ---

ID   : 14
NAME : my name here
MAIL : email@email.com
AGE  : 99
GEN  : male

--- options省略 ---

ID   : 14
NAME : 
MAIL : 
AGE  : 
GEN  : 


############## 特殊な記号 ##############

--- Splat Arguments ---

STATUS : fine
NAME   : sawada, sakata, suzuki, saito

--- 'xx=' method  ---

sawada
kato
suzuki
saito
テストだよ


############## 例外処理 ##############

--- 基本 ---

Not found. Hey! We got an error.
We found sawada in users!

--- 数回トライ ---

1回目のエラーだよ…
undefined method `finding_from_api' for main:Object
2回目のエラーだよ…
undefined method `finding_from_api' for main:Object
3回目のエラーだよ…
undefined method `finding_from_api' for main:Object
あきらめた!

何かありましたらコメントをどうぞ

comments powered by Disqus

人気の記事

950 Points チリ出身のギタリストが弾くドラゴンボールZがむちゃくちゃかっこいい…
774 Points Wordpress + Heroku + PostgreSQL + Amazon S3 = ¥0 / 無料でサイト運営
700 Points Rubyのチートシート 変数 / クラス / モジュール
524 Points Rubyのチートシート / アクティブサポート
451 Points 紙のデザイナーがウェブ開発できるようになるまでに必要なこと
435 Points Rails / Google Analyticsのデータを使って分析や管理画面のためのグラフをつくる
323 Points RailsとHerokuでノーティフィケーションをプッシュする / PusherとTurbolinksの兼ね合い
222 Points Rails / RSpec テスト書いたことない メンドクサイ(n´Д`)という時のチートシート
193 Points Rails / Ajaxを使って画面遷移しない一時保存機能をつける
193 Points Protractorでスクレイピングしてみた