在 Ruby 中重写实例变量数组的运算符

发布于 2024-08-09 19:04:25 字数 370 浏览 5 评论 0原文

抱歉,这个标题不好,我真的不知道该怎么称呼它。

我在 Ruby 中有这样的东西:

class Test
  def initialize
    @my_array = []
  end
  attr_accessor :my_array
end
test = Test.new
test.my_array << "Hello, World!"

对于 @my_array 实例变量,我想重写 << 运算符,以便我可以首先处理插入到的任何内容它。我已尝试使用 @my_array.<<(value) 作为类中的方法,但它不起作用。

Sorry for the poor title, I don't really know what to call this.

I have something like this in Ruby:

class Test
  def initialize
    @my_array = []
  end
  attr_accessor :my_array
end
test = Test.new
test.my_array << "Hello, World!"

For the @my_array instance variable, I want to override the << operator so that I can first process whatever is being inserted to it. I've tried @my_array.<<(value) as a method in the class, but it didn't work.

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(6

岁吢 2024-08-16 19:04:25

我想您正在寻找这个:

class Test
  def initialize
    @myarray = []
    class << @myarray
      def <<(val)
        puts "adding #{val}" # or whatever it is you want to do first
        super(val)
      end
    end
  end
  attr_accessor :myarray
end

了解 Ruby Singleton 类

I think you're looking for this:

class Test
  def initialize
    @myarray = []
    class << @myarray
      def <<(val)
        puts "adding #{val}" # or whatever it is you want to do first
        super(val)
      end
    end
  end
  attr_accessor :myarray
end

There's a good article about this and related topics at Understanding Ruby Singleton Classes.

等数载,海棠开 2024-08-16 19:04:25

我不确定这实际上是你可以直接做的事情。

您可以尝试从 Array 创建一个派生类,实现您的功能,例如:

class MyCustomArray < Array
  def initialize &process_append
    @process_append = &process_append
  end
  def << value
    raise MyCustomArrayError unless @process_append.call value
    super.<< value
  end
end

class Test
  def initialize
    @my_array = MyCustomArray.new
  end
  attr_accessor :my_array
end

I'm not sure that's actually something you can do directly.

You can try creating a derived class from Array, implementing your functionality, like:

class MyCustomArray < Array
  def initialize &process_append
    @process_append = &process_append
  end
  def << value
    raise MyCustomArrayError unless @process_append.call value
    super.<< value
  end
end

class Test
  def initialize
    @my_array = MyCustomArray.new
  end
  attr_accessor :my_array
end
椒妓 2024-08-16 19:04:25

干得好...

$ cat ra1.rb

class Aa < Array
  def << a
    puts 'I HAVE THE CONTROL!!'
    super a
  end
end

class Test
  def initialize
    @my_array = Aa.new
  end
  attr_accessor :my_array
end

test = Test.new
test.my_array << "Hello, World!"
puts test.my_array.inspect
$ ruby ra1.rb
I HAVE THE CONTROL!!
["Hello, World!"]
$ 

Here you go...

$ cat ra1.rb

class Aa < Array
  def << a
    puts 'I HAVE THE CONTROL!!'
    super a
  end
end

class Test
  def initialize
    @my_array = Aa.new
  end
  attr_accessor :my_array
end

test = Test.new
test.my_array << "Hello, World!"
puts test.my_array.inspect
$ ruby ra1.rb
I HAVE THE CONTROL!!
["Hello, World!"]
$ 
眼眸里的那抹悲凉 2024-08-16 19:04:25
a = []
a.instance_eval("alias old_add <<; def << value; puts value; old_add(value); end")

非常hackish,并且超出了我的想象......

只需用您想要执行的任何预处理更改“投入价值”即可。

a = []
a.instance_eval("alias old_add <<; def << value; puts value; old_add(value); end")

Very hackish, and off the top of my head ...

Just change 'puts value' with whatever preprocessing you want to do.

等数载,海棠开 2024-08-16 19:04:25

您可以扩展任何单个对象的元类,而无需创建全新的类:

>> i = []
=> []
>> class << i
>>   def <<(obj)
>>     puts "Adding "+obj.to_s
>>     super
>>   end
>> end
=> nil
>> i << "foo"
Adding foo
=> ["foo"]

You can extend the metaclass of any individual object, without having to create a whole new class:

>> i = []
=> []
>> class << i
>>   def <<(obj)
>>     puts "Adding "+obj.to_s
>>     super
>>   end
>> end
=> nil
>> i << "foo"
Adding foo
=> ["foo"]
青柠芒果 2024-08-16 19:04:25

我扩展了该类,创建了一个提供对实例变量的访问的方法。

        class KeywordBid
          def override_ignore_price(ignore_price)
            @ignorePrice = ignore_price
          end
        end

i extend the class, creating a method which provides access to the instance variable.

        class KeywordBid
          def override_ignore_price(ignore_price)
            @ignorePrice = ignore_price
          end
        end
~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文