假设现在有一组数据,如下图所示。
extend_id | out_id | sort_order 排序,越小越靠前 |
---|---|---|
1 | 20 | 255 |
2 | 80 | 255 |
3 | 20 | 253 |
4 | 80 | 253 |
5 | 20 | 252 |
6 | 80 | 252 |
7 | 80 | 254 |
8 | 20 | 254 |
9 | 20 | 3 |
10 | 20 | 3 |
11 | 20 | 4 |
12 | 20 | 3 |
方法1:用子查询:
SELECT *
FROM uploaded_extend a
WHERE (
SELECT count(*)
FROM uploaded_extend b
WHERE b.out_id=a.out_id AND b.sort_order < a.sort_order
) < 3
ORDER BY a.out_id DESC,a.sort_order ASC,a.extend_id DESC
解析:
Mysql执行顺序:
1.FROM uploaded_extend b
2.WHERE ...
3.SELECT *
4.ORDER BY a.out_id DESC,a.sort_order ASC,a.extend_id DESC
子查询同上
数据匹配过程:
a.extend_id = 1时,子查询返回7。
a.extend_id = 2时,子查询返回3。
a.extend_id = 3时,子查询返回5。
a.extend_id = 4时,子查询返回2,2<3符合条件,加入结果集。
a.extend_id = 5时,子查询返回5。
a.extend_id = 6时,子查询返回1,1<3符合条件,加入结果集。
..... 此处省略.....
方法2:用左链接:
SELECT a.*
FROM uploaded_extend a
LEFT JOIN uploaded_extend b ON b.out_id = a.out_id AND b.sort_order < a.sort_order
GROUP BY a.extend_id,a.out_id
having count(b.extend_id)<3
ORDER BY a.out_id DESC,a.sort_order ASC,a.extend_id DESC
方法3:用exists半连接:
SELECT * FROM `uploaded_extend` a
WHERE EXISTS
(
SELECT COUNT(*)
FROM `uploaded_extend` b
WHERE b.out_id=a.out_id AND b.sort_order < a.sort_order
HAVING COUNT(*)<3
)
ORDER BY a.out_id DESC,a.sort_order ASC,a.extend_id DESC
结果返回:
extend_id | out_id | sort_order |
---|---|---|
6 | 80 | 252 |
4 | 80 | 253 |
7 | 80 | 254 |
12 | 20 | 3 |
10 | 20 | 3 |
9 | 20 | 3 |