How can I override the []= method when subclassing

2019-07-02 14:49发布

I have a class that extends Hash, and I want to track when a hash key is modified.

What's the right syntax to override the [key]= syntactic method to accomplish this? I want to insert my code, then call the parent method.

Is this possible with the C methods? I see from the docs that the underlying method is

rb_hash_aset(VALUE hash, VALUE key, VALUE val)

How does that get assigned to the bracket syntax?

标签: ruby hash
3条回答
在下西门庆
2楼-- · 2019-07-02 15:10
class MyHash < Hash
  def []=(key,value)
    super
  end
end
查看更多
戒情不戒烟
3楼-- · 2019-07-02 15:11

I think using set_trace_func is more general solution

class MyHash < Hash
  def initialize
    super
  end

  def []=(key,val)
    super
  end
end

set_trace_func proc { |event, file, line, id, binding, classname|
  printf "%10s %8s\n", id, classname if classname == MyHash
}

h = MyHash.new
h[:t] = 't'

#=>
initialize   MyHash
initialize   MyHash
initialize   MyHash
       []=   MyHash
       []=   MyHash
       []=   MyHash
查看更多
SAY GOODBYE
4楼-- · 2019-07-02 15:23

The method signature is def []=(key, val), and super to call the parent method. Here's a full example:

class MyHash < Hash
  def []=(key,val)
    printf("key: %s, val: %s\n", key, val)
    super(key,val)
  end
end

x = MyHash.new

x['a'] = 'hello'
x['b'] = 'world'

p x
查看更多
登录 后发表回答