スポンサーサイト
カテゴリ: スポンサー広告
[Rails][Ruby]みんなで使おうtapp
カテゴリ: Rails
デバックのお友達tapp!!
rubyに標準のtapではないですよ?tappです!
pが2つです
そもそもtapってなに?
class Object
def tap
yield(self)
self
end
end
実装はこんだけ! なんとも単純な、そして奥深いメソッドです
ソースコードを拝借するとこんな使い方をしています
ary.map{|x| x**2}.tap{|a| p a}.select {|x| x>10 } # => [16]メソッドチェインしていく際の途中結果を出力するのに使っています
こんなサンプルもありました
参考 : [Ruby]RubyのObject#tapメソッドの使い道。
[1].tap {|x| 5.times {|i| x << x.pop * i.succ } }[0]
# => 120上記URLへいけばわかりますが、injectでも同等の機能が実現できます
ん?使い道なくね?
こういう使い方もあるようです
[Ruby]RbyのObject#tapメソッドの使い道がわかった。
まとめると、使い道がなかなか難しいメソッド
使うとしたらメソッドチェインの途中で結果を出力するくらい
つまり主にデバック用、でもうまく使うとかっこいいメソッド
tappの出番だ!
もう割り切ってtapはデバック用だ!という人はtappにしましょう
tappのインストール
gem install tapp
Gemfileであれば
gem 'tapp'
tappの使い方
さきほどの例を利用したサンプルを掲示します
[1,2,3,4,5].map{|x| x**2}.tap{|a| p a}.select {|x| x>10 }結果
[1, 4, 9, 16, 25]
=> [16, 25]
1行目がtap{|a| p a}の結果です
2行目が式全体の結果です
tappを使うと...
[1,2,3,4,5].map{|x| x**2}.tapp.select {|x| x>10 }短くなりました!なんというデバック専用メソッドでしょう
tappでこんなこともできます
x**2の部分の結果を逐次出したい場合は。。。
[1,2,3,4,5].map{|x| (x**2).tapp}.tapp.select {|x| x>10 }結果は以下のようになります
1
4
9
16
25
[1, 4, 9, 16, 25]
=> [16, 25]
メソッドチェインしている場合に楽ちんですね
tapとtappのちょっと実用例
Rspecを例にとってtappでバグを含んだテストを見つける方法です
context "sizeメソッドでraiseする" do
it do
x=[1,2,3].stub(:size).and_raise(StandardError)
y=[1,2,3].tap{|o| o.stub(:size).and_raise(StandardError)}
expect{ x.tapp.size }.should raise_error
expect{ y.tapp.size }.should raise_error
end
end
この結果は以下のように出力されます
StandardError
[1, 2, 3]
このテストはPassします
しかし、sizeメソッドがraiseを送出することを想定してStubを定義したはずなのに、
stubの記述方法が間違っている為、
実はx.sizeを実行した際のNoMethodErrorでパスしていることになります
tappの結果をみるとxのppはStandardError,
yのppは[1,2,3]と想定どおりの配列であることが見て取れます
あまりよくわからないサンプルですね。。。
どちらかというとtapのサンプルになっています
オブジェクト定義とstub定義を同時に行うときにtapは便利だったりしますよ!
間違ってもxのようにしないように!
tappについて
- 関連記事
- [Rails]Hash#from_xml (04/03)
- [Rails]memoizeでクラスメソッドのメモ化のdeprecatedの対処方法 (04/01)
- Rails3 ActiveSupport::Concern (03/01)
- Ruby1.9.2と1.9.3のencodeメソッド (02/16)
- [Ubuntu]Mongodb2.0系のインストール手順と使い方メモ (01/10)
- [Rails3.2]Rails3.2.0.rc2のメモ (01/09)
- 分散オブジェクトストレージシステム「STF」をインストールしてみたよ [導入編] (01/01)
- 分散オブジェクトストレージシステム「STF」をインストールしてみたよ [ミドルウェア編] (12/31)
- [Ruby]LevenshteinDistanceを使ったメールアドレス誤入力検知 (12/25)
- [Rails3] 管理画面とフロント画面のroutesの綺麗な分離方法 (11/08)




