【问题标题】:Ruby diff two hashes and merge in loop with cumulative sumRuby 区分两个哈希并在循环中合并累积和
【发布时间】:2018-09-17 05:47:06
【问题描述】:

需要红宝石的帮助!

我收集了有关 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。但这会扭曲真实的状态。

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

所以,我创建了另外两个哈希值:“h2”和“h3”。 'h3' 的值在每一轮循环中都会重置,这会存储(子)域的所有 PID,其 utime 如下所示:

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 用于 disseapear,我需要将它们从“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}

【问题讨论】:

  • 正如我所描述的,预期的输出是域名及其累积运行时间,换句话说:在运行此脚本期间,特定域的所有 PHP 进程消耗了多少 CPU 运行时间。

标签: ruby hash diff cumulative-sum accumulator


【解决方案1】:

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

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)}
  }
}

【讨论】:

  • 谢谢@Chiranjib,你的代码看起来很有用。我可以问您将代码中的哈希结构调整为与我的相同吗?我更新了我的帖子,并详细说明了哈希的外观。谢谢!
  • 嘿@Brian,稍微改了一下。您应该掌握这个想法并尝试自己实现逻辑。另外,如果有帮助,请采纳答案。
  • 再次感谢。我的意思是哈希结构,而不是它的名称。例如,这是我的哈希: "domain1" => [ {:pid => XXX, :utime => ZZZ }, {:pid => XXX1, :utime => ZZZ1 } ], "domain2" => [ {: pid => XXX, :utime => ZZZ }, {:pid => XXX1, :utime => ZZZ1 } ] 和你的看起来有点不同。我的 h1 哈希看起来也有点不同。对不起,我真的是红宝石初学者。非常感谢您的帮助。
  • 我以为你想要一个域的累积 utimes,看起来你还想收集域的 pid 信息?这个问题在这里非常不清楚。在上面的评论中,“domain1”不是哈希,而是哈希数组。如果是这种情况,那么 h1 应该具有类似 h1 = {:domain1 => [...], :domain2 => [...]} 的结构
  • 是的,但是为了了解域的累积 utime,我还需要知道 pids 及其 utime 并知道哪个进程是新的或已经消失的,基于此我可以将其 utime 总结为总运行时间计数。您的示例很好,但不完全对应于我的哈希和哈希数组。我又一次更新了我的帖子。 h2 和 h3 应该看起来像 {"domain1"=>[{:pid=>2, :utime=>20}, {:pid=>1, :utime=>10}], "domain2"=>[{: pid=>1, :utime=>10}, {:pid=>3, :utime=>30}]} 请再检查一下我帖子中的代码示例。为我不清楚的描述道歉
猜你喜欢
  • 2017-12-18
  • 2016-01-06
  • 2012-01-11
  • 2016-09-02
  • 2010-12-02
  • 2011-02-21
  • 2022-11-02
  • 2021-02-02
  • 1970-01-01
相关资源
最近更新 更多