【问题标题】:How to group by rows with most recent order?如何按最近订单的行分组?
【发布时间】:2014-06-28 09:09:57
【问题描述】:

更新:

Here is the demo 和当前结果基于 M Khalid Junaid 的回答。查询仍然没有输出我的预期结果。

我有一个非常简单的表格,这里是值。

id      animal_id       latitude    longitude   created_at
--------------------------------------------------------------------------
119     75          1.356203    103.828140  2014-04-30 15:00:04
118     75          1.296613    103.857079  2014-04-30 14:58:58
117     75          1.296613    103.857079  2014-04-30 14:58:20
116     75          1.296613    103.857079  2014-04-30 14:53:17

这是我的查询,如果 latitudelongitudeuser_id 相同,我想进行 GROUP。

select p.id,p.animal_id,p.name,p.latitude,p.longitude,p.created_at from Photo p
        where 5 >= (select count(*)
                    from Photo p2
                    where p2.animal_id = p.animal_id and
                          p2.id <= p.id
                   )
        AND DATE(p.created_at) > DATE_SUB(NOW(),INTERVAL 13 DAY)
        AND ( p.latitude BETWEEN 0.908862 AND 1.717581 ) AND ( p.longitude BETWEEN 103.584595 AND 104.098206 )
        GROUP BY p.latitude,p.longitude,p.animal_id
        ORDER BY p.created_at DESC;

当前结果 id = 116

id      animal_id       latitude    longitude   created_at
--------------------------------------------------------------------------
119     75          1.356203    103.828140  2014-04-30 15:00:04
116     75          1.296613    103.857079  2014-04-30 14:53:17

预期结果 id = 118

我想在分组 latitude,longitude,uer_id

时获得最近的结果
id      animal_id       latitude    longitude   created_at
--------------------------------------------------------------------------
119     75          1.356203    103.828140  2014-04-30 15:00:04
118     75          1.296613    103.857079  2014-04-30 14:58:58

我尝试了几种方法,但都没有得到想要的结果。

【问题讨论】:

  • 这是一个常见问题解答
  • ...animal_id 是从哪里来的?!
  • animal_id 在同一个表中,所以不需要加入任何外部表。
  • 数据集中没有animal_id。要么将其包含在数据集中,要么将其从查询中排除
  • 糟糕!我的错。我已经更新了这个问题。 user_id 应该是 animal_id。请在此处查看sqlfiddle.com/#!2/7bd16/1

标签: mysql groupwise-maximum


【解决方案1】:

这可能是一个棘手的解决方案。您可以像这样在 group 语句中连接 latitude,longitude,animal_id

group by concat(latitude, longitude, animal_id)

【讨论】:

    【解决方案2】:

    我终于找到了自己的答案。感谢大家分享您的时间。

    SELECT p.id,p.animal_id,p.latitude,p.longitude,p.created_at 
    
    -- This will make sure that `GROUP BY` will pickup most recent result
    FROM (SELECT id,animal_id,latitude,longitude,created_at from Photo ORDER BY id DESC) p
    
    -- Pick 5 rows for each animal_id. Meaning, there can be multiple photo of animal but MAX is 5.
    WHERE 5 >= (select count(*)
                        from (SELECT * from Photo p4 GROUP BY latitude,longitude,animal_id) p2
                        where p2.animal_id = p.animal_id and
                              p2.id >= p.id 
                       )
    
    -- We want Photos uploaded 5 days ago
    AND DATE(p.created_at) > DATE_SUB(NOW(),INTERVAL 15 DAY)
    
    -- Plus, only photos within given Map Bound
    AND ( p.latitude BETWEEN 0.908862 AND 1.717581 ) AND ( p.longitude BETWEEN 103.584595 AND 104.098206 )                   
    
    -- This will help to remove duplicate images in same location of same animal. We will see only most recent photo in each exact lat,lng location
    GROUP BY p.latitude,p.longitude,p.animal_id
    
    ORDER BY id DESC; 
    

    【讨论】:

      【解决方案3】:

      使用自加入,group by 的结果是不确定的,不能保证你是该组的最新行

      select p.id,p.animal_id,
      p.latitude,p.longitude,p.created_at 
      from Photo p
      JOIN (SELECT MAX(id) id,latitude,longitude,animal_id
       FROM Photo 
      GROUP BY latitude,longitude,animal_id
      ) p1 ON(p.id = p1.id)
      where 5 >= (select count(*)
                  from Photo p2
                  where p2.animal_id = p.animal_id and
                  p2.id <= p.id)
      AND DATE(p.created_at) > DATE_SUB(NOW(),INTERVAL 13 DAY)       
      AND ( p.latitude BETWEEN 0.908862 AND 1.717581 ) 
      AND ( p.longitude BETWEEN 103.584595 AND 104.098206 )
      GROUP BY p.latitude,p.longitude,p.animal_id
      ORDER BY p.created_at DESC;
      

      Demo

      【讨论】:

      • 感谢您的回答。我已经根据我当前的数据库更新了数据集。如果可能,请帮我再次检查。我在这里分享的数据集是第一次执行的结果,所以它根本不正确。对此感到抱歉。
      猜你喜欢
      • 1970-01-01
      • 2018-09-01
      • 2016-08-31
      • 2015-09-15
      • 2017-01-06
      • 1970-01-01
      • 1970-01-01
      • 2018-07-02
      • 1970-01-01
      相关资源
      最近更新 更多