因此,我尝试做的是调用Reporting API来过滤所有可能的细分(按网站,广告客户,广告类型,广告系列等细分报告......)。但是,有一个问题是,每次登录时,故障都是唯一的。
示例:
["site","advertiser","ad_type","campaign","line_items"]
["campaign","position","line_items"]
当我第一次为此报告API构建代码时,我只有一个登录名要进行测试,因此我对维度(["site","advertiser","ad_type","campaign","line_items"]
)进行了硬编码。所以我所做的就是为sites
的报告创建了API。然后,对于每个site
,为advertisers
和每个advertiser
进行ping操作,我会为下一个维度进行操作,依此类推......让我留下~6层的嵌套循环。< / p>
基本上我正在做的事情:
sites = mechanize.get "#{base_ur}/report?dim=sites"
sites = Yajl::Parser.parse(sites.body) # json parser
sites.each do |site|
advertisers = mechanize.get "#{base_ur}/report?site=#{site.fetch("id")}&dim=advertiser"
advertisers = Yajl::Parser.parse(advertisers.body) # json parser
advertisers.each do |advertiser|
ad_types = mechanize.get "#{base_ur}/report?site=#{site.fetch("id")}&advertiser=#{advertiser.fetch("id")}&dim=ad_type"
ad_types = Yajl::Parser.parse(ad_types.body) # json parser
ad_types.each do |ad_type|
...and so on...
end
end
end
GET <api_url>/?dim=<dimension to breakdown>&site=<filter by site id>&advertiser=<filter by advertiser id>...etc...
在嵌套循环结束时,我留下了一份尽可能细化的报告。
现在这很有用,因为我只想到有一条崩溃路径,但显然每个帐户都有不同的维度细分。
所以我要问的是,如果给出一系列细分,我如何设置一个嵌套循环来动态地遍历粒度奇点?
感谢。
答案 0 :(得分:1)
我不确定你的JSON / GET究竟返回什么,但对于像这样的问题,你需要递归。
也许这样的事情?它不是很优雅,绝对可以进一步优化,但希望能给你一个想法。
some_hash = {:id=>"site-id", :body=>{:id=>"advertiser-id", :body=>{:id=>"ad_type-id", :body=>{:id=>"something-id"}}}}
@breakdowns = ["site", "advertiser", "ad_type", "something"]
def recursive(some_hash, str = nil, i = 0)
if @breakdowns[i+1].nil?
str += "#{@breakdowns[i]}=#{some_hash[:id]}"
else
str += "#{@breakdowns[i]}=#{some_hash[:id]}&dim=#{@breakdowns[i + 1]}"
end
p str
some_hash[:body].is_a?(Hash) ? recursive(some_hash[:body], str.gsub(/dim.*/, ''), i + 1) : return
end
recursive(some_hash, 'base-url/report?')
=> "base-url/report?site=site-id&dim=advertiser"
=> "base-url/report?site=site-id&advertiser=advertiser-id&dim=ad_type"
=> "base-url/report?site=site-id&advertiser=advertiser-id&ad_type=ad_type-id&dim=something"
=> "base-url/report?site=site-id&advertiser=advertiser-id&ad_type=ad_type-id&something=something-id"
答案 1 :(得分:0)
如果您只是想要映射数据,可以按另一个用户指出的方式递归映射到散列。如果你实际上是想在循环中对这些数据做一些事情,并且想要动态地重新创建你在问题中列出的循环结构(虽然我建议提出一个不同的解决方案),你可以使用元编程如下:
require 'active_support/inflector'
# Assume we are given an input of breakdowns
# I put 'testarr' in place of the operations you perform on each local variable
# for brevity and so you can see that the code works.
# You will have to modify to suit your needs
result = []
testarr = [1,2,3]
b = binding
breakdowns.each do |breakdown|
snippet = <<-END
eval("#{breakdown.pluralize} = testarr", b)
eval("#{breakdown.pluralize}", b).each do |#{breakdown}|
END
result << snippet
end
result << "end\n"*breakdowns.length
eval(result.join)
注意:这种方法可能不受欢迎,正如我所说,我确定还有其他方法可以完成你想要做的事情。