【问题标题】:Is it possible to call multiple methods or objects at once?是否可以一次调用多个方法或对象?
【发布时间】:2014-10-20 16:11:17
【问题描述】:

假设我有一个方法,其中包含一个计数器,该计数器在每次滴答时将其计数输出到屏幕。 在程序的其他地方,调用此方法的新版本,因此它们都/全部同时运行,具有不同的计数器,并与滴答声一起更新。 Ruby可以做到这一点吗?通常创建一个对象的另一个实例是我会做的,尽管我对 Ruby 还是新手并且掌握了它的窍门。

我将在稍后尝试实现的示例代码进行编辑。我目前在手机上,无法使用电脑。

【问题讨论】:

    标签: ruby loops object methods counter


    【解决方案1】:

    在这里,我创建了 Counter 的两个实例,两个计数器最初都设置为 0。然后我每隔 3 秒启动它们 - 每个都在自己的线程中。他们开始打印数字。

    class Counter
      def initialize
        @counter = 0 # initial counter to 0
      end
    
      def run
        loop do
          # wait one second, print the counter and increase it
          sleep 1
          puts @counter
          @counter += 1
        end
      end
    end
    
    threads = []
    
    2.times do
      # put each counter in a separate thread
      threads << Thread.new do
        counter = Counter.new
        counter.run
      end
    
      sleep 3 # make a pause between launching counters    
    end
    
    threads.each(&:join)
    

    我得到的输出:

    0 # first
    1 # first
    2 # first
    0 # second
    3 # first
    1 # second
    4 # first
    2 # second
    5 # first
    

    这里唯一的技巧是使用Thread 类,否则第二个计数器将永远无法开始工作,因为第一个计数器会阻塞整个过程。

    【讨论】:

    • 这太棒了!我尝试实现它的方式是,我需要它不断地从对象中添加和减去,它变得越来越忙。信不信由你,我最终使用了 2d 数组并使用 shift/unshift 来获取计数器。这是最奇怪的方法,但它似乎奏效了。不过,我会记住这些以供将来参考。非常感谢您的帮助!
    【解决方案2】:

    您可以使用队列和外部循环,例如:

    class Counter
    
      def initialize(start)
        @count = start
      end
    
      def tick
        @count += 1
        puts @count
      end
    
    end
    
    queue = []
    queue << Counter.new(0)
    queue << Counter.new(100)
    
    5.times do |i|
      puts "--- tick #{i} ---"
      queue.each(&:tick)
      sleep 1
    end
    

    输出:

    --- tick 0 ---
    1
    101
    --- tick 1 ---
    2
    102
    --- tick 2 ---
    3
    103
    --- tick 3 ---
    4
    104
    --- tick 4 ---
    5
    105
    

    5.times 循环中,tick 被发送到队列中的每个项目。请注意,这些方法是按照计数器添加到队列中的顺序调用的,即它们不会同时调用。

    【讨论】:

    • 我其实很喜欢这个方法,和我最后做的差不多。我只是担心在更大的情况下使用大量数组。
    • @Rockster160 queue 数组只存储 2 个 Counter 实例,而不是每个刻度。
    【解决方案3】:

    出于您的目的,您可以使用事件循环、进程或线程。因为在一般情况下,Ruby 会在方法执行时被阻塞(直到它返回控制权为return)。

    class ThreadCounter
      def run
        @thread ||= Thread.new do
          i = 0
          while !@stop do
            puts i+=1
            sleep(1)
          end
          @stop = nil
        end
      end
    
      def stop
        @stop = true
        @thread && @thread.join
      end
    end
    
    counter1 = ThreadCounter.new
    counter2 = ThreadCounter.new
    counter1.run
    counter2.run
    # wait some time
    counter1.stop
    counter2.stop
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多