代码之家  ›  专栏  ›  技术社区  ›  Gdeglin

以类似的时间戳对结果进行分组

  •  1
  • Gdeglin  · 技术社区  · 15 年前

    在我的项目中,我希望从我的数据库中选择记录,然后根据在某个时间范围内与最新记录相似的时间发生的记录将它们分组在一起。

    例如,时间范围为1小时。如果用户在下午4:30到5:15之间创建了3篇文章,在下午1:15到1:30之间创建了2篇文章,在上午10:00创建了1篇文章,我希望创建如下结构:

    user.posts.find(:all).group_by do |post|
      # (posts have a created_at column containing both a date and time)
      # Algorithm here
    end
    

    结果:

    [
     [Tue March 31 5:15pm, [post6,post5,post4]]
     [Tue March 31 1:30pm, [post3,post2]]
     [Tue March 31 10:00am, [post1]]
    ]
    

    编辑: 谢谢你,乔尔。以下是我最终使用的代码(feed而不是post):

      def aggregate(feeds, timeLimit)
        return [] if feeds.blank?
        result = []
        bin = []
        feeds = feeds.sort_by { |f| -f.created_at.to_i }
        bin_time = feeds.first.created_at
        feeds.each do |feed|
          if (bin_time - feed.created_at) < timeLimit
            bin << feed
          else
            result << [bin_time, bin]
            bin_time = feed.created_at
            bin = [feed]
          end
        end
        result << [bin_time, bin]
        result
      end
    
    2 回复  |  直到 15 年前
        1
  •  1
  •   Joel Bender    15 年前

    基本概念非常简单,将帖子累积到垃圾桶中,然后当时间超出范围时,启动一个新的垃圾桶。以下是Python版本:

    posts = [('post6', 1715), ('post5', 1645), ('post4', 1630)
        , ('post3', 1330), ('post2', 1315), ('post1', 1000)
        ]
    
    rslt = []
    bin = []
    binTime = 1 << 31
    for postData, postTime in posts:
        if (postTime >= binTime - 100):
            bin.append(postData)
        else:
            if bin:
                rslt.append([binTime, bin])
            binTime = postTime
            bin = [postData]
    
    if bin:
        rslt.append([binTime, bin])
    
    print rslt
    
        2
  •  0
  •   dwc    15 年前
    if post.created_at - group_start > limit
        output current group if non-empty
        set group to current post
        set group_start to post.created_at
    else
        add post to current group
    

    然后,在循环外部,如果非空,则输出当前组。根据访问帖子的顺序调整if条件。