2013-04-25 15 views
5

は、私が(http://ruby-doc.org/stdlib-1.9.3/libdoc/csv/rdoc/CSV.htmlを参照)RubyでCSVクラスは、いくつかのショートカットのインタフェースを持っていることに気付きました:Ruby:ブロックを受け入れるクラス?

CSV    { |csv_out| csv_out << %w{my data here} } # to $stdout 
CSV(csv = "") { |csv_str| csv_str << %w{my data here} } # to a String 
CSV($stderr) { |csv_err| csv_err << %w{my data here} } # to $stderr 
CSV($stdin)  { |csv_in| csv_in.each { |row| p row } } # from $stdin 

自分のクラスのためにこれを行う方法はありますか?私はDSLを実装しているので、コードをもっときれいにすることができます。

答えて

6

これはクラスではありません。 Objectで定義されたメソッドです(同じ名前のクラスがありますが、CSV)。リンクしたドキュメントは誤解を招くようなものです。 Thisはそれをよりよく説明します。

モジュールではそうはできませんが、ブロックをとるメソッドを定義できます。

1

あなたが示した例は、メソッドなしで呼び出されたクラスではありません。反対に、クラスなしで呼び出されるメソッドです。 sawaは既にexplainedの動作をしています。

Ruby 2.0がRefinementsを導入しました。

Objectをカスタマイズしてカスタムメソッドを追加し、質問の例のように使用することができます。

Ruby 1.9を使用している場合は、修正する代わりに猿のパッチを適用することができます。

しかし、これはコードがよりスパゲティッシュで、手続き的で、オブジェクト指向でなくなる可能性があるため、2度考えるべきです。

+0

「リファインメント」リンクありがとうございます。 –

+2

'refine'の全目的は、monkey-patchが見える範囲を制御することです。これらの 'CSV'メソッドがどこからでも見えるようにしたいので、洗練を使う必要はありません。 –

関連する問題