Ruby 1.9.2 リファレンスマニュアル > ライブラリ一覧 > 組み込みライブラリ > Methodクラス

class Method

クラスの継承リスト: Method < Object < Kernel < BasicObject

Abstract

Object#method によりオブジェクト化され たメソッドオブジェクトのクラスです。

メソッドの実体(名前でなく)とレシーバの組を封入します。 Proc オブジェクトと違ってコンテキストを保持しません。

Proc との差

Method は取り出しの対象であるメソッドが なければ作れませんが、Proc は準備なしに作れます。その点から Proc は使い捨てに向き、Method は何度も繰り返し生成する 場合に向くと言えます。また内包するコードの大きさという点では Proc は小規模、Method は大規模コードに向くと言えます。

既存のメソッドを Method オブジェクト化する。

class Foo
  def foo(arg)
    "foo called with arg #{arg}"
  end
end

m = Foo.new.method(:foo)

p m             # => #<Method: Foo#foo>
p m.call(1)     # => "foo called with arg 1"

名前のないメソッド(の代わり)が必要なら Proc を使うと良い。

pr = Proc.new {|arg|
  "proc called with arg #{arg}"
}

p pr            # => #<Proc:0x401b1fcc>
p pr.call(1)    # => "proc called with arg 1"

Method オブジェクトが有用なのは以下のような場合。

class Foo
  def foo() "foo" end
  def bar() "bar" end
  def baz() "baz" end
end

obj = Foo.new

# 任意のキーとメソッドの関係をハッシュに保持しておく
methods = {1 => obj.method(:foo),
           2 => obj.method(:bar),
           3 => obj.method(:baz)}

# キーを使って関連するメソッドを呼び出す
p methods[1].call       # => "foo"
p methods[2].call       # => "bar"
p methods[3].call       # => "baz"

しかし、レシーバを固定させる(Method オブジェクトはレシーバを保持する)必 要がないなら Object#sendを使う方法も有用。

class Foo
  def foo() "foo" end
  def bar() "bar" end
  def baz() "baz" end
end

# 任意のキーとメソッド(の名前)の関係をハッシュに保持しておく
# レシーバの情報がここにはないことに注意
methods = {1 => :foo,
           2 => :bar,
           3 => :baz}

# キーを使って関連するメソッドを呼び出す
# レシーバは任意(Foo クラスのインスタンスである必要もない)
p Foo.new.send(methods[1])      # => "foo"
p Foo.new.send(methods[2])      # => "bar"
p Foo.new.send(methods[3])      # => "baz"

@see Object#method

インスタンスメソッド

self == other -> bool
self === other -> bool

自身と other が同じインスタンスの同じメソッドを表す場合に true を返します。そうでない場合に false を返します。

[PARAM] other:
自身と比較したいオブジェクトを指定します。
s = "bar"
a = s.method(:size)
b = s.method(:size)
p a == b                            #=> true

[SEE_ALSO] Method#eql?

self[*args] -> object
call(*args) -> object
call(*args) { ... } -> object

メソッドオブジェクトに封入されているメソッドを起動します。

引数やブロックはそのままメソッドに渡されます。

self[] の形の呼び出しは通常のメソッド呼び出しに見た目を 近付けるためだけに用意されたもので、Array#[]のような 他の [] メソッドとの意味的な関連性はありません。

メソッドオブジェクトが汚染されている場合、そのメソッドは、セーフレ ベル 4 で実行されます ([[unknown:セキュリティモデル/セーフレベルに関するその他の詳細]]を参照)。

[PARAM] args:
self に渡される引数。
arity -> Fixnum

メソッドが受け付ける引数の数を返します。

ただし、メソッドが可変長引数を受け付ける場合、負の整数

-(必要とされる引数の数 + 1)

を返します。C 言語レベルで実装されたメソッドが可変長引数を 受け付ける場合、-1 を返します。

例:

class C
  def u;               end
  def v(a);            end
  def w(*a);           end
  def x(a, b);         end
  def y(a, b, *c);     end
  def z(a, b, *c, &d); end
end

c = C.new
p c.method(:u).arity     #=> 0
p c.method(:v).arity     #=> 1
p c.method(:w).arity     #=> -1
p c.method(:x).arity     #=> 2
p c.method(:y).arity     #=> -3
p c.method(:x).arity     #=> -3

s = "xyz"
s.method(:size).arity      #=> 0
s.method(:replace).arity   #=> 1
s.method(:squeeze).arity   #=> -1
s.method(:count).arity     #=> -1
eql?(other) -> bool
equal?(other) -> bool

指定された other が self 自身である場合のみ真を返します。 これは Object クラスで定義されたデフォルトの動作で す。

[PARAM] other:
自身と比較したいオブジェクトを指定します。
s = "bar"
a = s.method(:size)
b = s.method(:size)
p a.eql?(b)          #=> false
p a.eql?(a)          #=> true

[SEE_ALSO] Method#==

hash -> Integer

自身の Object#object_id を返します。 これは Object クラスで定義されたデフォルトの動作です。

inspect -> String

self を読みやすい文字列として返します。

以下の形式の文字列を返します。

#<Method: klass1(klass2)#method>                (形式1)

klass1 は、Method#inspect では、レシーバのクラス名、 UnboundMethod#inspect では、UnboundMethod オブジェクトの生成 元となったクラス/モジュール名です。

klass2 は、実際にそのメソッドを定義しているクラス/モジュール名、 method は、メソッド名を表します。

module Foo
  def foo
    "foo"
  end
end
class Bar
  include Foo
  def bar
  end
end

p Bar.new.method(:foo)        # => #<Method: Bar(Foo)#foo>
p Bar.new.method(:bar)        # => #<Method: Bar(Bar)#bar>

klass1 と klass2 が同じ場合は以下の形式になります。

#<Method: klass1#method>                        (形式2)

特異メソッドに対しては、

#<Method: obj.method>                           (形式3)
#<Method: klass1(klass2).method>                (形式4)

という形式の文字列を返します。二番目の形式では klass1 はレシーバ、 klass2 は実際にそのメソッドを定義しているオブジェクトになります。

# オブジェクトの特異メソッド
obj = ""
class <<obj
  def foo
  end
end
p obj.method(:foo)      # => #<Method: "".foo>

# クラスメソッド(クラスの特異メソッド)
class Foo
  def Foo.foo
  end
end
p Foo.method(:foo)      # => #<Method: Foo.foo>

# スーパークラスのクラスメソッド
class Bar < Foo
end
p Bar.method(:foo)      # => #<Method: Bar(Foo).foo>

# 以下は(形式1)の出力になる
module Baz
  def baz
  end
end

class <<obj
  include Baz
end
p obj.method(:baz)      # => #<Method: Object(Baz)#baz>

[SEE_ALSO] Object#inspect

name -> Symbol

このメソッドの名前を返します。

owner -> Class | Module

このメソッドが定義されている class か module を返します。

receiver -> object

このメソッドオブジェクトのレシーバを返します。

to_proc -> Proc

self を call する Proc オブジェクトを生成して返します。

unbind -> UnboundMethod

self のレシーバとの関連を取り除いた UnboundMethod オブ ジェクトを生成して返します。

Methods

Classes