这是我的Ruby代码

方法getLikes()使用 token hash以用户的t格式获取Facebook赞。

def multi
    token = ["Facebook token 1","Facebook token 2","Facebook token 3",...]
    @data = []
    @threads = []

    token.each do |t|
        @threads << Thread.new{@data << getLikes(t)}
    end

    @threads.each do |th|
        th.join
    end


    render json: @data
end

问题在于,由于进行了Parallization,@data的内容的数据顺序不同。

为了解决这个问题,我将第一个循环修改为
i = 0
token.each do |t|
    @threads << Thread.new{@data[i] = getLikes(t)}
    i = i + 1
end

但是,然后程序不会等待所有线程完成。我在null数组中得到了一些@data值。

什么是解决这个问题的好方法?

谢谢

最佳答案

问题是您的代码不是线程安全的,因为它使用线程间的共享变量而不使用互斥体。哈希在Ruby中不是线程安全的。

解决方案是在线程中返回简单值,并将结果汇​​总到您的主代码中。为了保持顺序,只需将 token 和值一起返回:

def multi
  token = ["Facebook token 1","Facebook token 2","Facebook token 3",...]
  @threads = []

  token.each do |t|
    @threads << Thread.new{[t, getLikes(t)]}
  end

  data = Hash[@threads.map(&:value)] # this will block the main thread

  sorted_data = []
  token.each do |t|
    sorted_data << data[t]
  end

  render json: sorted_data
end

10-08 09:23