Ruby diff两个散列并与累积和循环合并

时间:2018-09-17 05:47:07

标签: ruby hash diff cumulative-sum accumulator

需要红宝石的帮助!

我有一个循环,可以收集有关PHP进程的数据(PID,utimes)。我有两个哈希。第一个“ h1”看起来像:

"domain1" => { :utime => 0, :last_seen => 0, :process_count => 0, :process_count_avg => 0 },
"domain2" => { :utime => 0, :last_seen => 0, :process_count => 0, :process_count_avg => 0 }

这是它的代码:

h1[vhostname] ||= { :utime => 0, :last_seen => 0, :process_count => 0, :process_count_avg => 0 }
h1[vhostname][:utime] += utime_proc 
h1[vhostname][:last_seen] = 0

“ vhostname”是包含域名的字符串。 'utime_proc'是一个utime值。

在每个循环中,我对特定域的所有进程的所有utime求和,输出是Domain及其求和的utime。但这会扭曲真实状态。

我需要做的是使特定域的utime累计。为所有当前进程的utime之和,但为所有已结束进程的utime之和。我可能必须为每个子域utime存储pid进程,如果该进程消失,则其最后一个utime将添加到默认值(“ h1”哈希):该域的utime。

因此,我再创建两个哈希:'h2'和'h3'。 “ h3”的值在每个循环中都将重置,并且它使用其utime来存储(sub)domain的所有PID,如下所示:

h3[vhostname] = []
h3[vhostname] << {:pid => pid, :utime => utime_proc}

“ h2”哈希存储之前所有循环的PID,与“ h3”相同,但不会重置:

if not h2.key?(vhostname)
h2[vhostname] = []
h2[vhostname] << {:pid => pid, :utime => utime_proc}
end

输出哈希应类似于:

{"domain1"=>[{:pid=>2, :utime=>20}, {:pid=>1, :utime=>10}], "domain2"=>[{:pid=>1, :utime=>10}, {:pid=>3, :utime=>30}]}

现在我需要帮助: 1.可能需要比较这两个哈希值,如果要散布使用PID,则需要将它们从“ h2”哈希值中删除,并将其最后一个utime值加到存储在“ h1”中的utime值。 2.我为域显示了新的PID(“ h3”是新的pid,尚未在“ h2”中),将该PID添加到“ h2”,并将其utime添加到特定域。

这些是我无法做到的。我知道我可以做到:

'h2-h3'或'h3-h2',但我不知道如何处理结果以及如何处理它。

伙计们,您能帮我吗?我的代码的简短版本如下。我还是红宝石新手。

h1 = {}
# Hash to collect PID and its utimes
h2 = {}

loop do  

# Hash to temporarly store PID and its utimes - in each cycle is reseting
h3 = {}

# Here I collect processes
#############
#############

# Collect PIDs and its utimes
# Store PIDs and its utimes temporarly - only for this loop round
h3[vhostname] = []
h3[vhostname] << {:pid => pid, :utime => utime_proc}

# is h2 empty? if so, this is probably first loop round
if not h2.key?(vhostname)
h2[vhostname] = []
h2[vhostname] << {:pid => pid, :utime => utime_proc}
else
# h2 is not empty, we can diff and sum
# PROBABLY PLACE I NEED TO HELP WITH

end
# Here I do some more magic with h1 and output the result with some delay
end

更新

我将h2和h3哈希结构更改为:

{:domain => "domain1.com", :pid => XXXX, :utime => YYYYY}

1 个答案:

答案 0 :(得分:0)

我不会尝试实现您的逻辑,但是我将尽力处理散列。为了简单起见,我没有循环,只是处理了测试数据

domains = ['domain1','domain2','domain3']

h1 = {}
h2 = {}
# generate blank template for each domain
domains.each { |vhostname|
  h1[vhostname] ||= { :utime => 0, :last_seen => 0, :process_count => 0, :process_count_avg => 0 }
  h2[vhostname] ||= {}
}

# dummy loop
1.upto(5) {
  h3={}
  # start collecting data for each domain
  domains.each { |vhostname|
    # TEST DATA
    h3[vhostname] ||= {}
    1.upto(5) {
      _pid = rand(1..10)
      h3[vhostname][:"#{_pid}"] ||= {:utime => rand(9999)}
    }
    # TEST DATA

    h2[vhostname].merge!(h3[vhostname])
    h2[vhostname].each { |proc, details|
      unless h3[vhostname].key?(proc)
        h1[vhostname][:utime] = h1[vhostname][:utime] + details[:utime]
      end
    }
    h2[vhostname] = h2[vhostname].keep_if { |proc| h3[vhostname].key?(proc)}
  }
}