Object 클래스
Object 클래스
Object는 모든 Ruby 객체의 기본 루트예요. Object는 대체 객체 계층을 만들 수 있게 해 주는 BasicObject를 상속해요. Object의 메서드는 명시적으로 오버라이드하지 않는 한 모든 클래스에서 사용할 수 있어요.
출처: Ruby 3.3 API
본문
Object는 Kernel 모듈을 믹스인해서 내장 커널 함수를 전역적으로 접근 가능하게 해 줘요. Object의 인스턴스 메서드는 Kernel 모듈이 정의하지만, 명확성을 위해 여기에서 문서화하기로 했어요.
Object를 상속하는 클래스에서 상수를 참조할 때 전체 네임스페이스를 쓸 필요가 없어요. 예를 들어 YourClass 안에서 File을 참조하면 최상위 File 클래스를 찾아요.
Object의 메서드 설명에서 파라미터 symbol은 symbol을 가리켜요. symbol은 따옴표로 묶인 문자열이거나 Symbol(예: :name)이에요.
여기에 있는 것 (What's Here)
먼저, 다른 곳에 있는 것. class Object:
BasicObject클래스에서 상속받아요.Kernel모듈을 include해요.
여기, class Object는 다음을 위한 메서드를 제공해요: Querying, Instance Variables, Other
Querying
!~:self가 주어진 객체와 일치하지 않으면true, 그렇지 않으면false를 반환해요.<=>:self와 주어진 객체object가 같은 객체이거나self == object이면 0, 그렇지 않으면nil을 반환해요.===: case 동등성을 구현해요. 사실상==를 호출하는 것과 같아요.eql?: hash 동등성을 구현해요. 사실상==를 호출하는 것과 같아요.kind_of?(is_a?별칭): 주어진 인자가self의 singleton 클래스의 조상인지 반환해요.instance_of?:self가 주어진 클래스의 인스턴스인지 반환해요.instance_variable_defined?: 주어진 인스턴스 변수가self에 정의돼 있는지 반환해요.method:self에서 주어진 메서드의Method객체를 반환해요.methods:self의 public·protected 메서드의 symbol 이름 배열을 반환해요.nil?:false를 반환해요. (nil만nil?메서드에true로 응답해요)object_id:self에 대응하는 정수 중 현재 프로세스에서 고유한 값을 반환해요.private_methods:self의 private 메서드의 symbol 이름 배열을 반환해요.protected_methods:self의 protected 메서드의 symbol 이름 배열을 반환해요.public_method:self에서 주어진 public 메서드의Method객체를 반환해요.public_methods:self의 public 메서드의 symbol 이름 배열을 반환해요.respond_to?:self가 주어진 메서드에 응답하는지 반환해요.singleton_class:self의 singleton 클래스를 반환해요.singleton_method:self에서 주어진 singleton 메서드의Method객체를 반환해요.singleton_methods:self의 singleton 메서드의 symbol 이름 배열을 반환해요.define_singleton_method:self에 주어진 symbol 메서드 이름과 블록 또는 proc으로 singleton 메서드를 정의해요.extend:self의 singleton 클래스에 주어진 모듈들을 include해요.public_send:self의 주어진 public 메서드를 주어진 인자와 함께 호출해요.send:self의 주어진 메서드를 주어진 인자와 함께 호출해요.
Instance Variables
instance_variable_get:self의 주어진 인스턴스 변수 값을 반환하고, 인스턴스 변수가 설정돼 있지 않으면nil을 반환해요.instance_variable_set:self의 주어진 인스턴스 변수 값을 주어진 객체로 설정해요.instance_variables:self의 인스턴스 변수의 symbol 이름 배열을 반환해요.remove_instance_variable:self에서 이름이 주어진 인스턴스 변수를 제거해요.
Other
clone: singleton 클래스와 동결 상태를 포함한self의 얕은 복사본을 반환해요.define_singleton_method:self에 주어진 symbol 메서드 이름과 블록 또는 proc으로 singleton 메서드를 정의해요.display:self를 주어진IO스트림 또는$stdout에 출력해요.dup:self의 동결되지 않은 얕은 복사본을 반환해요.enum_for(to_enum별칭): 주어진 메서드·인자·블록을 사용해self를 위한Enumerator를 반환해요.extend:self의 singleton 클래스에 주어진 모듈들을 include해요.freeze:self에 대한 추가 수정을 막아요.hash:self의 정수 hash 값을 반환해요.inspect:self의 사람이 읽을 수 있는 문자열 표현을 반환해요.itself:self를 반환해요.method_missing:self에서 정의되지 않은 메서드가 호출될 때 호출되는 메서드예요.public_send:self의 주어진 public 메서드를 주어진 인자와 함께 호출해요.send:self의 주어진 메서드를 주어진 인자와 함께 호출해요.to_s:self의 문자열 표현을 반환해요.
상수 (Constants)
- ARGF
Public Class Methods
yaml_tag (url)
YAML 태그를 등록해요.
Public Instance Methods
obj !~ other → true or false
=~ 메서드를 사용해 두 객체가 일치하지 않으면 true, 그렇지 않으면 false를 반환해요.
obj <=> other → 0 or nil
obj와 other가 같은 객체이거나 obj == other이면 0, 그렇지 않으면 nil을 반환해요.
<=>은 다양한 메서드가 객체를 비교하는 데 써요. 예를 들어 Enumerable#sort, Enumerable#max 등이요.
<=>의 구현은 -1, 0, 1, nil 중 하나를 반환해야 해요. -1은 self가 other보다 작다는 뜻, 0은 같다는 뜻, 1은 크다는 뜻, nil은 두 값을 비교할 수 없다는 뜻이에요.
<=>을 정의하면 Comparable을 include해서 <=, <, ==, >=, >, between? 메서드를 얻을 수 있어요.
true === other → true or false
true 또는 false를 반환해요.
Object#==처럼, object가 Object의 인스턴스이면(그 많은 하위클래스 중 하나가 아니라) true예요.
이 메서드는 보통 그 하위클래스들이 case 문에서 의미 있는 의미를 제공하도록 오버라이드해요.
CSV (*args, **options, &block)
args를 CSV::instance에 전달해요.
CSV("CSV,data").read
#=> [["CSV", "data"]]
블록이 주어지면 인스턴스가 블록에 전달되고 반환값이 블록의 반환값이 돼요.
CSV("CSV,data") { |c|
c.read.any? { |a| a.include?("data") }
} #=> true
CSV("CSV,data") { |c|
c.read.any? { |a| a.include?("zombies") }
} #=> false
CSV 옵션도 주어질 수 있어요.
io = StringIO.new
CSV(io, col_sep: ";") { |csv| csv << ["a", "b", "c"] }
이 API는 Ractor-safe하지 않아요.
DelegateClass (superclass, &block)
이 라이브러리의 기본 인터페이스예요. 클래스를 정의할 때 위임을 설정하는 데 사용해요.
class MyClass < DelegateClass(ClassToDelegateTo) # Step 1
def initialize
super(obj_of_ClassToDelegateTo) # Step 2
end
end
또는:
MyClass = DelegateClass(ClassToDelegateTo) do # Step 1
def initialize
super(obj_of_ClassToDelegateTo) # Step 2
end
end
다음은 Tempfile에서 쓰는 사용 예시인데, Tempfile은 정말로 저장 위치와 File이 삭제돼야 할 시점에 대한 몇 가지 특별한 규칙만 있는 File 객체예요. 위임 사용법의 거의 교과서적인 완벽한 예시죠.
class Tempfile < DelegateClass(File)
# constant and class member data initialization...
def initialize(basename, tmpdir=Dir::tmpdir)
# build up file path/name in var tmpname...
@tmpfile = File.open(tmpname, File::RDWR|File::CREAT|File::EXCL, 0600)
# ...
super(@tmpfile)
# below this point, all methods of File are supported...
end
# ...
end
Digest(name) → digest_subclass
온디맨드 로딩이 포함된 경우에도 스레드 안전한 방식으로 name으로 Digest 하위클래스를 반환해요.
require 'digest'
Digest("MD5")
# => Digest::MD5
Digest(:SHA256)
# => Digest::SHA256
Digest(:Foo)
# => LoadError: library not found for class Digest::Foo -- digest/foo
define_singleton_method(symbol, method) → symbol
수신자에 public singleton 메서드를 정의해요. method 파라미터는 Proc, Method 또는 UnboundMethod 객체일 수 있어요. 블록이 지정되면 메서드 본문으로 쓰여요. 블록이나 메서드에 파라미터가 있으면 그 파라미터가 메서드 파라미터로 쓰여요.
class A
class << self
def class_name
to_s
end
end
end
A.define_singleton_method(:who_am_i) do
"I am: #{class_name}"
end
A.who_am_i # ==> "I am: A"
guy = "Bob"
guy.define_singleton_method(:hello) { "#{self}: Hello there!" }
guy.hello #=> "Bob: Hello there!"
chris = "Chris"
chris.define_singleton_method(:greet) {|greeting| "#{greeting}, I'm Chris!" }
chris.greet("Hi") #=> "Hi, I'm Chris!"
display(port = $>) → nil
주어진 port에 self를 써요.
1.display
"cat".display
[ 4, 5, 6 ].display
puts
출력:
1cat[4, 5, 6]
dup → an_object
obj의 얕은 복사본을 만들어요. obj의 인스턴스 변수는 복사되지만, 그들이 참조하는 객체는 복사되지 않아요.
이 메서드는 클래스 특유 동작이 있을 수 있어요. 있다면 그 동작은 클래스의 #initialize_copy 메서드 아래에 문서화돼 있어요.
dup vs clone에 대하여
일반적으로 clone과 dup는 하위클래스에서 다른 의미를 가질 수 있어요. clone은 내부 상태를 포함해 객체를 복제하는 데 쓰이고, dup는 전형적으로 하위 객체의 클래스를 사용해 새 인스턴스를 만들어요.
dup을 쓰면 객체가 확장된 모듈은 복사되지 않아요.
class Klass
attr_accessor :str
end
module Foo
def foo; 'foo'; end
end
s1 = Klass.new #=> #<Klass:0x401b3a38>
s1.extend(Foo) #=> #<Klass:0x401b3a38>
s1.foo #=> "foo"
s2 = s1.clone #=> #<Klass:0x401be280>
s2.foo #=> "foo"
s3 = s1.dup #=> #<Klass:0x401c1084>
s3.foo #=> NoMethodError: undefined method `foo' for #<Klass:0x401c1084>
enum_for(method = :each, *args) → enum
obj에서 method를 호출해(있으면 args를 전달해) 열거하는 새 Enumerator를 만들어요. method가 yield한 것이 enumerator의 값이 돼요.
블록이 주어지면 반복할 필요 없이 enumerator의 크기를 계산하는 데 쓰여요(Enumerator#size 참고).
예시
str = "xyz"
enum = str.enum_for(:each_byte)
enum.each { |b| puts b }
# => 120
# => 121
# => 122
# protect an array from being modified by some_method
a = [1, 2, 3]
some_method(a.to_enum)
# String#split in block form is more memory-effective:
very_large_string.split("|") { |chunk| return chunk if chunk.include?('DATE') }
# This could be rewritten more idiomatically with to_enum:
very_large_string.to_enum(:split, "|").lazy.grep(/DATE/).first
일반적인 Enumerable용 메서드를 정의할 때 블록이 전달되지 않는 경우를 위해 to_enum을 호출하는 것이 전형적이에요.
파라미터 전달과 크기 산정 블록이 있는 예시가 있어요.
module Enumerable
# a generic method to repeat the values of any enumerable
def repeat(n)
raise ArgumentError, "#{n} is negative!" if n < 0
unless block_given?
return to_enum(__method__, n) do # __method__ is :repeat here
sz = size # Call size and multiply by n...
sz * n if sz # but return nil if size itself is nil
end
end
each do |*val|
n.times { yield *val }
end
end
end
%i[hello world].repeat(2) { |w| puts w }
# => Prints 'hello', 'hello', 'world', 'world'
enum = (1..14).repeat(3)
# => returns an Enumerator when called without a block
enum.first(4) # => [1, 1, 1, 2]
enum.size # => 42
obj == other → true or false
동등성 — Object 레벨에서 ==는 obj와 other가 같은 객체일 때만 true를 반환해요. 보통 이 메서드는 하위클래스에서 클래스 특유 의미를 제공하도록 오버라이드돼요.
==와 달리 equal? 메서드는 객체 동일성(즉, a가 b와 같은 객체일 때에만 a.equal?(b))을 판정하는 데 쓰이므로 하위클래스가 절대 오버라이드하면 안 돼요:
obj = "a"
other = obj.dup
obj == other #=> true
obj.equal? other #=> false
obj.equal? obj #=> true
eql? 메서드는 obj와 other가 같은 hash 키를 참조하면 true를 반환해요. Hash가 멤버 동등성을 테스트하는 데 쓰여요. eql?이 true를 반환하는 어떤 객체 쌍에 대해서도 두 객체의 hash 값은 같아야 해요. 그래서 eql?을 오버라이드하는 하위클래스는 hash도 적절히 오버라이드해야 해요.
Object 클래스의 객체에 대해 eql?은 ==와 동의어예요. 하위클래스는 보통 오버라이드된 ==에 eql?을 별칭으로 해 이 전통을 이어가지만, 예외가 있어요. 예를 들어 Numeric 타입은 ==에서는 타입 변환을 수행하지만 eql?에서는 수행하지 않아요. 그래서:
1 == 1.0 #=> true
1.eql? 1.0 #=> false
extend(module, ...) → obj
각 모듈에서 주어진 파라미터의 인스턴스 메서드를 obj에 추가해요.
module Mod
def hello
"Hello from Mod.\n"
end
end
class Klass
def hello
"Hello from Klass.\n"
end
end
k = Klass.new
k.hello #=> "Hello from Klass.\n"
k.extend(Mod) #=> #<Klass:0x401b3bc8>
k.hello #=> "Hello from Mod.\n"
freeze → obj
obj에 대한 추가 수정을 막아요. 수정을 시도하면 FrozenError가 발생해요. 동결된 객체를 동결 해제할 방법은 없어요. Object#frozen?도 참고해요.
이 메서드는 self를 반환해요.
a = [ "a", "b", "c" ]
a.freeze
a << "z"
다음과 같은 출력이 나와요.
prog.rb:3:in `<<': can't modify frozen Array (FrozenError)
from prog.rb:3
다음 클래스의 객체는 항상 동결돼 있어요: Integer, Float, Symbol.
hash → integer
이 객체의 정수 hash 값을 생성해요. 이 함수는 a.eql?(b)이면 a.hash == b.hash를 의미하는 속성을 가져야 해요.
hash 값은 eql?과 함께 Hash 클래스가 두 객체가 같은 hash 키를 참조하는지 판정하는 데 쓰여요. Integer의 용량을 초과하는 hash 값은 쓰기 전에 잘려요.
객체의 hash 값은 Ruby의 호출이나 구현 사이에 동일하지 않을 수 있어요. Ruby 호출·구현 사이에 안정적인 식별자가 필요하면 커스텀 메서드로 만들어야 해요.
Integer 같은 특정 핵심 클래스는 내장 hash 계산을 사용하고, hash 키로 쓰일 때 hash 메서드를 호출하지 않아요.
여러 값에 기반한 hash를 직접 구현할 때는 배열의 hash 코드를 사용해 클래스와 값들을 결합하는 게 모범 사례예요.
예:
def hash
[self.class, a, b, c].hash
end
그 이유는 Array#hash 메서드가 이미 여러 hash 값을 안전하고 효율적으로 결합하는 로직을 갖고 있기 때문이에요.
inspect → string
obj의 사람이 읽을 수 있는 표현을 담은 문자열을 반환해요. 기본 inspect는 객체의 클래스 이름, 메모리 주소의 인코딩, 그리고 인스턴스 변수와 그 값(각각에 inspect를 호출해)의 목록을 보여 줘요. 사용자 정의 클래스는 obj의 더 나은 표현을 제공하도록 이 메서드를 오버라이드해야 해요. 오버라이드할 때는 기본 외부 인코딩과 호환되는 인코딩의 문자열을 반환해야 해요.
[ 1, 2, 3..4, 'five' ].inspect #=> "[1, 2, 3..4, \"five\"]"
Time.new.inspect #=> "2008-03-08 19:43:39 +0900"
class Foo
end
Foo.new.inspect #=> "#<Foo:0x0300c868>"
class Bar
def initialize
@bar = 1
end
end
Bar.new.inspect #=> "#<Bar:0x0300c868 @bar=1>"
instance_of?(class) → true or false
obj가 주어진 클래스의 인스턴스이면 true를 반환해요. Object#kind_of?도 참고해요.
class A; end
class B < A; end
class C < B; end
b = B.new
b.instance_of? A #=> false
b.instance_of? B #=> true
b.instance_of? C #=> false
instance_variable_defined?(symbol) → true or false
주어진 인스턴스 변수가 obj에 정의돼 있으면 true를 반환해요. String 인자는 symbol로 변환돼요.
class Fred
def initialize(p1, p2)
@a, @b = p1, p2
end
end
fred = Fred.new('cat', 99)
fred.instance_variable_defined?(:@a) #=> true
fred.instance_variable_defined?("@b") #=> true
fred.instance_variable_defined?("@c") #=> false
instance_variable_get(symbol) → obj
주어진 인스턴스 변수의 값을 반환하고, 인스턴스 변수가 설정돼 있지 않으면 nil을 반환해요. 일반 인스턴스 변수는 변수 이름의 @ 부분이 포함돼야 해요. 제공된 symbol이 인스턴스 변수 이름으로 유효하지 않으면 NameError 예외를 던져요. String 인자는 symbol로 변환돼요.
class Fred
def initialize(p1, p2)
@a, @b = p1, p2
end
end
fred = Fred.new('cat', 99)
fred.instance_variable_get(:@a) #=> "cat"
fred.instance_variable_get("@b") #=> 99
instance_variable_set(symbol, obj) → obj
symbol이 가리키는 인스턴스 변수를 주어진 객체로 설정해요. 이는 클래스 작성자가 의도한 캡슐화를 우회할 수 있으므로 주의해서 써야 해요. 변수는 이 호출 전에 존재할 필요가 없어요. 인스턴스 변수 이름이 문자열로 전달되면 symbol로 변환돼요.
class Fred
def initialize(p1, p2)
@a, @b = p1, p2
end
end
fred = Fred.new('cat', 99)
fred.instance_variable_set(:@a, 'dog') #=> "dog"
fred.instance_variable_set(:@c, 'cat') #=> "cat"
fred.inspect #=> "#<Fred:0x401b3da8 @a=\"dog\", @b=99, @c=\"cat\">"
instance_variables → array
수신자의 인스턴스 변수 이름 배열을 반환해요. 단순히 접근자를 정의한다고 대응하는 인스턴스 변수가 만들어지는 건 아니에요.
class Fred
attr_accessor :a1
def initialize
@iv = 3
end
end
Fred.new.instance_variables #=> [:@iv]
is_a?(class) → true or false, kind_of?(class) → true or false
class가 obj의 클래스이거나, obj의 상위클래스 중 하나이거나, obj에 include된 모듈 중 하나이면 true를 반환해요.
module M; end
class A
include M
end
class B < A; end
class C < B; end
b = B.new
b.is_a? A #=> true
b.is_a? B #=> true
b.is_a? C #=> false
b.is_a? M #=> true
b.kind_of? A #=> true
b.kind_of? B #=> true
b.kind_of? C #=> false
b.kind_of? M #=> true
itself → obj
수신자를 반환해요.
string = "my string"
string.itself.object_id == string.object_id #=> true
method(sym) → method
obj에서 이름이 주어진 메서드를 수신자로 조회해 Method 객체(또는 NameError)를 반환해요. Method 객체는 obj의 객체 인스턴스 안의 클로저처럼 동작하므로, 인스턴스 변수와 self의 값이 계속 사용 가능해요.
class Demo
def initialize(n)
@iv = n
end
def hello()
"Hello, @iv = #{@iv}"
end
end
k = Demo.new(99)
m = k.method(:hello)
m.call #=> "Hello, @iv = 99"
l = Demo.new('Fred')
m = l.method("hello")
m.call #=> "Hello, @iv = Fred"
Method가 to_proc 메서드를 구현하므로 반복자와 함께 쓸 수 있다는 점을 참고해요.
[ 1, 2, 3 ].each(&method(:puts)) # => prints 3 lines to stdout
out = File.open('test.txt', 'w')
[ 1, 2, 3 ].each(&out.method(:puts)) # => prints 3 lines to file
require 'date'
%w[2017-03-01 2017-03-02].collect(&Date.method(:parse))
#=> [#<Date: 2017-03-01 ((2457814j,0s,0n),+0s,2299161j)>, #<Date: 2017-03-02 ((2457815j,0s,0n),+0s,2299161j)>]
methods(regular=true) → array
obj의 public·protected 메서드 이름 목록을 반환해요. obj의 조상에서 접근 가능한 모든 메서드를 포함해요. 선택 파라미터가 false면 obj의 public·protected singleton 메서드 배열을 반환하고, obj에 include된 모듈의 메서드는 포함하지 않아요.
class Klass
def klass_method()
end
end
k = Klass.new
k.methods[0..9] #=> [:klass_method, :nil?, :===,
# :==~, :!, :eql?
# :hash, :<=>, :class, :singleton_class]
k.methods.length #=> 56
k.methods(false) #=> []
def k.singleton_method; end
k.methods(false) #=> [:singleton_method]
module M123; def m123; end end
k.extend M123
k.methods(false) #=> [:singleton_method]
nil? → true or false
nil 객체만 nil?에 true로 응답해요.
Object.new.nil? #=> false
nil.nil? #=> true
id → integer
obj의 정수 식별자를 반환해요.
주어진 객체의 object_id 호출마다 같은 숫자가 반환되고, 두 개의 활성 객체가 id를 공유하지 않아요.
참고: 내장 클래스의 일부 객체는 최적화를 위해 재사용돼요. 즉시 값과 동결된 문자열 리터럴이 그 경우예요.
BasicObject는 __id__를, Kernel은 object_id를 구현해요.
즉시 값은 참조로 전달되지 않고 값으로 전달돼요: nil, true, false, Fixnum, Symbol, 일부 Float.
Object.new.object_id == Object.new.object_id # => false
(21 * 2).object_id == (21 * 2).object_id # => true
"hello".object_id == "hello".object_id # => false
"hi".freeze.object_id == "hi".freeze.object_id # => true
private_methods(all=true) → array
obj에서 접근 가능한 private 메서드 목록을 반환해요. all 파라미터가 false로 설정되면 수신자의 메서드만 나열돼요.
protected_methods(all=true) → array
obj에서 접근 가능한 protected 메서드 목록을 반환해요. all 파라미터가 false로 설정되면 수신자의 메서드만 나열돼요.
public_method(sym) → method
method와 비슷하지만 public 메서드만 검색해요.
public_methods(all=true) → array
obj에서 접근 가능한 public 메서드 목록을 반환해요. all 파라미터가 false로 설정되면 수신자의 메서드만 나열돼요.
public_send(symbol [, args...]) → obj
symbol이 가리키는 메서드를 호출하고, 지정된 인자들을 전달해요. send와 달리 public_send는 public 메서드만 호출해요. 메서드가 문자열로 식별되면 문자열은 symbol로 변환돼요.
1.public_send(:puts, "hello") # causes NoMethodError
remove_instance_variable(symbol) → obj
obj에서 이름이 주어진 인스턴스 변수를 제거하고, 그 변수의 값을 반환해요. String 인자는 symbol로 변환돼요.
class Dummy
attr_reader :var
def initialize
@var = 99
end
def remove
remove_instance_variable(:@var)
end
end
d = Dummy.new
d.var #=> 99
d.remove #=> 99
d.var #=> nil
respond_to?(symbol, include_all=false) → true or false
obj가 주어진 메서드에 응답하면 true를 반환해요. optional 두 번째 파라미터가 true로 평가될 때만 private·protected 메서드가 검색에 포함돼요.
메서드가 구현되지 않은 경우(Windows의 Process.fork, GNU/Linux의 File.lchmod 등) false가 반환돼요.
메서드가 정의되지 않으면 respond_to_missing? 메서드가 호출되고 그 결과가 반환돼요.
메서드 이름 파라미터가 문자열로 주어지면 문자열은 symbol로 변환돼요.
respond_to_missing?(symbol, include_all) → true or false
이것을 직접 쓰지 마세요.
obj가 id 메서드에 응답할 수 있는지 반환하는 훅 메서드예요.
메서드 이름 파라미터가 문자열로 주어지면 문자열은 symbol로 변환돼요.
respond_to?와 BasicObject의 예시를 참고해요.
send(symbol [, args...]) → obj
symbol이 가리키는 메서드를 호출하고, 지정된 인자들을 전달해요. 메서드가 문자열로 식별되면 문자열은 symbol로 변환돼요.
BasicObject는 __send__를, Kernel은 send를 구현해요. obj가 Socket 같은 같은 메서드 이름을 가질 때는 __send__가 send보다 안전해요. public_send도 참고해요.
class Klass
def hello(*args)
"Hello " + args.join(' ')
end
end
k = Klass.new
k.send :hello, "gentle", "readers" #=> "Hello gentle readers"
singleton_class → class
obj의 singleton 클래스를 반환해요. obj에 singleton 클래스가 없으면 새로 만들어요.
obj가 nil, true, false이면 각각 NilClass, TrueClass, FalseClass를 반환해요. obj가 Integer, Float, Symbol이면 TypeError를 던져요.
Object.new.singleton_class #=> #<Class:#<Object:0xb7ce1e24>>
String.singleton_class #=> #<Class:String>
nil.singleton_class #=> NilClass
singleton_method(sym) → method
method와 비슷하지만 singleton 메서드만 검색해요.
class Demo
def initialize(n)
@iv = n
end
def hello()
"Hello, @iv = #{@iv}"
end
end
k = Demo.new(99)
def k.hi
"Hi, @iv = #{@iv}"
end
m = k.singleton_method(:hi)
m.call #=> "Hi, @iv = 99"
m = k.singleton_method(:hello) #=> NameError
singleton_methods(all=true) → array
obj의 singleton 메서드 이름 배열을 반환해요. 선택 all 파라미터가 true면 obj에 include된 모듈의 메서드도 목록에 포함돼요. public·protected singleton 메서드만 반환돼요.
module Other
def three() end
end
class Single
def Single.four() end
end
a = Single.new
def a.one()
end
class << a
include Other
def two()
end
end
Single.singleton_methods #=> [:four]
a.singleton_methods(false) #=> [:two, :one]
a.singleton_methods #=> [:two, :one, :three]
to_enum(method = :each, *args) → enum
obj에서 method를 호출해(있으면 args를 전달해) 열거하는 새 Enumerator를 만들어요. method가 yield한 것이 enumerator의 값이 돼요.
블록이 주어지면 반복할 필요 없이 enumerator의 크기를 계산하는 데 쓰여요(Enumerator#size 참고).
예시
str = "xyz"
enum = str.enum_for(:each_byte)
enum.each { |b| puts b }
# => 120
# => 121
# => 122
# protect an array from being modified by some_method
a = [1, 2, 3]
some_method(a.to_enum)
# String#split in block form is more memory-effective:
very_large_string.split("|") { |chunk| return chunk if chunk.include?('DATE') }
# This could be rewritten more idiomatically with to_enum:
very_large_string.to_enum(:split, "|").lazy.grep(/DATE/).first
일반적인 Enumerable용 메서드를 정의할 때 블록이 전달되지 않는 경우를 위해 to_enum을 호출하는 것이 전형적이에요.
파라미터 전달과 크기 산정 블록이 있는 예시가 있어요.
module Enumerable
# a generic method to repeat the values of any enumerable
def repeat(n)
raise ArgumentError, "#{n} is negative!" if n < 0
unless block_given?
return to_enum(__method__, n) do # __method__ is :repeat here
sz = size # Call size and multiply by n...
sz * n if sz # but return nil if size itself is nil
end
end
each do |*val|
n.times { yield *val }
end
end
end
%i[hello world].repeat(2) { |w| puts w }
# => Prints 'hello', 'hello', 'world', 'world'
enum = (1..14).repeat(3)
# => returns an Enumerator when called without a block
enum.first(4) # => [1, 1, 1, 2]
enum.size # => 42
to_s → string
obj를 나타내는 문자열을 반환해요. 기본 to_s는 객체의 클래스와 객체 id의 인코딩을 출력해요. 특별한 경우로, Ruby 프로그램의 초기 실행 컨텍스트인 최상위 객체는 "main"을 반환해요.
to_yaml(options = {})
객체를 YAML로 변환해요. 사용 가능한 options에 대한 자세한 내용은 Psych.dump를 참고해요.
xmp (exps, bind = nil)
IRB::XMP 표준 라이브러리를 require할 때만 사용 가능한 편의 메서드예요.
주어진 표현식을 exps 파라미터로, 선택 바인딩을 bind로(또는 최상위 바인딩을) 사용해 새 XMP 객체를 만들어요. 그런 다음 :XMP 프롬프트 모드로 주어진 표현식을 평가해요.
예:
require 'irb/xmp'
ctx = binding
xmp 'foo = "bar"', ctx
#=> foo = "bar"
#==>"bar"
ctx.eval 'foo'
#=> "bar"
자세한 내용은 XMP.new 참고.