2011-03-11 4 views
3

ruby에 Python __getattr__과 동일한 기능이 있습니까? (적어도 방법을 찾는 데 사용됩니까?)ruby ​​객체가 임의의 메시지에 응답하도록 만드시겠습니까?

class X(object): 
    def __getattr__(self, name): 
     return lambda x: print("Calling " + name + ": " + x) 

x = X() 
x.some_method("some args") 

그래서 같은 수 :

class X 
    # .. ??? .. 
    def default_action(method_name, x) 
     puts "Calling {method_name}: {x}" 
    end 
end 

x = X.new() 
x.some_method("some args") 

답변

7

예. 객체가 메시지에 응답하지 않으면, 루비는 수신기에 메시지 선택과 method_missing 메시지와 인수를 보낼 것입니다 : 당신이 method_missing를 정의하면, 당신은 또한 그에 따라 respond_to_missing?을 정의해야

class X 
    def method_missing(selector, *args, &blk) 
    puts "The message was #{selector.inspect}." 
    puts "The arguments were #{args.map(&:inspect).join(', ')}." 
    puts "And there was #{blk ? 'a' : 'no'} block." 
    super 
    end 
end 

x = X.new 
x.some_method('some args', :some_other_args, 42) 
# The message was :some_method. 
# The arguments were "some args", :some_other_args, 42. 
# And there was no block. 
# NoMethodError: undefined method `some_method' 

x.some_other_method do end 
# The message was :some_other_method. 
# The arguments were . 
# And there was a block. 
# NoMethodError: undefined method `some_other_method' 

참고. 그렇지 않으면이 같은 이상한 행동을 얻을 다음과 같이이 특정 경우

x.respond_to?(:foo) # => false 
x.foo    # Works. Huh? 

을, 우리가 모든 메시지를 처리, 그러므로 우리는 간단하게 정의 할 수 있습니다 :

class X; def respond_to_missing?(*) true end end 

x.respond_to?(:foo) # => true 
-2
class Test 
    def say 
    puts "hi" 
    end 
end 

을 당신은

obj = Test.new 
obj.send "say" 

으로 말할 메소드를 호출 할 수

obj.respond_to? "say" 
,536를 사용하는 방법 가용성을 확인

마지막으로, 모두 함께

if (obj.respond_to? "say") 
    obj.send "say" 
end 
+0

-1 즉, 전혀 관계가없는 일입니다. 질문을 다시 읽으십시오. – delnan

+0

아, 내 잘못 .. 질문을 잘못 읽고 .. :( – RameshVel

2

IIRC를 넣어, 당신은이 문제를 처리하기 위해 루비 클래스에 method_missing을 정의 할 수 있습니다. 미안하지만 구체적인 정보는 제공 할 수 없습니다.

5
class X 
    def method_missing(sym,*args) 
    puts "Method #{sym} called with #{args}" 
    end 
end 
a = X.new 
a.blah("hello","world") 

#=> Method blah called with ["hello", "world"] 
관련 문제