我设置了 sinatra,监听来自 github repo 的提交。我目前设置的系统,侦听帖子,然后将有效负载推送到有效负载数组。然后我打电话
@@payloads.each do .... whatever
如果来自 github 的多个帖子,即人们在@@payloads.each
运行时推送更多提交,会发生什么?如果有一个有效载荷,然后另一个被推送,payloads.each
调用是否会再次循环?或者它.each
是否设置为一旦呼叫完成,呼叫通过的有效负载数量就固定下来了?
我设置了 sinatra,监听来自 github repo 的提交。我目前设置的系统,侦听帖子,然后将有效负载推送到有效负载数组。然后我打电话
@@payloads.each do .... whatever
如果来自 github 的多个帖子,即人们在@@payloads.each
运行时推送更多提交,会发生什么?如果有一个有效载荷,然后另一个被推送,payloads.each
调用是否会再次循环?或者它.each
是否设置为一旦呼叫完成,呼叫通过的有效负载数量就固定下来了?
作为仅供参考,除非您同步访问,否则您可能会遇到读取/写入同一数组的问题。查看 Ruby 内置的Queue类。它是线程的一部分。
您可以有多个不会发生冲突的生产者/消费者。这是文档中的内容:
此类提供了一种在线程之间同步通信的方法。
例子:
require 'thread'
queue = Queue.new
producer = Thread.new do
5.times do |i|
sleep rand(i) # simulate expense
queue << i
puts "#{i} produced"
end
end
consumer = Thread.new do
5.times do |i|
value = queue.pop
sleep rand(i/2) # simulate expense
puts "consumed #{value}"
end
end
consumer.join
至于使用each
循环数组,我认为在语法上你应该使用:
loop do
break if @@payloads.empty?
end
each
意味着要迭代的有限元素集。描述说:
为 self.. 中的每个元素调用一次给定块。
在其他语言中,您无法更改正在迭代的容器,因为元素的数量是在循环开始时设置的;尝试更改容器将引发错误。依靠each
允许您这样做可能会导致期望您会在其他语言中看到这种行为;在我看来,您依赖的是副作用或侧门,这不是一个好习惯。
loop
并不意味着因为这是一个简单的循环,您必须有条件地摆脱使用自己的逻辑。这是示例loop
:
loop do
print "Input: "
line = gets
break if !line or line =~ /^qQ/
# ...
end
没有元素数量的假设,它完全是开放式的。而且,很容易突破,因为 Queue 有这个必要的empty?
方法。
那是我的 0.02 美元,我会怎么做。
查看页面右侧的“相关”主题以获得更多想法。
只要@@payloads
是标准 ruby 数组,推送的有效负载就应该包含在#each
迭代中。
当一个线程迭代一个数组,而另一个线程追加到同一个数组时,迭代线程将包含追加的项目。
看看这个要点,它有一个简单的程序来演示这种行为。一个线程迭代,而另一个线程添加到数组中。由于 ruby 中线程调度的性质,每次结果都可能不同。