一种)
您可以使用随每一行递增并随每个 user_ID 重置的变量来获取行数。
SELECT ID,
User_ID,
`Order`
FROM ( SELECT @r:= IF(@u = User_ID, @r + 1,1) AS `Order`,
ID,
User_ID,
@u:= User_ID
FROM Photos,
(SELECT @r:= 1) AS r,
(SELECT @u:= 0) AS u
ORDER BY User_ID, ID
) AS Photos
SQL Fiddle 示例
二)
我的第一个解决方案是添加Order
到添加行号的排序中,因此任何具有Order
Gets 的内容首先按其顺序排序,但这仅在您的排序系统没有间隙并且从 1 开始时才有效:
SELECT ID,
User_ID,
RowNumber AS `Order`
FROM ( SELECT @r:= IF(@u = User_ID, @r + 1,1) AS `RowNumber`,
ID,
User_ID,
@u:= User_ID
FROM Photos,
(SELECT @i:= 1) AS r,
(SELECT @u:= 0) AS u
ORDER BY User_ID, `Order`, ID
) AS Photos
ORDER BY `User_ID`, `Order`
Order
使用字段的示例
有间隙订购
我最终找到了一种即使在序列中有间隙时也能保持排序顺序的方法。
SELECT ID, User_ID, `Order`
FROM Photos
WHERE `Order` IS NOT NULL
UNION ALL
SELECT Photos.ID,
Photos.user_ID,
Numbers.RowNum
FROM ( SELECT ID,
User_ID,
@r1:= IF(@u1 = User_ID,@r1 + 1,1) AS RowNum,
@u1:= User_ID
FROM Photos,
(SELECT @r1:= 0) AS r,
(SELECT @u1:= 0) AS u
WHERE `Order` IS NULL
ORDER BY User_ID, ID
) AS Photos
INNER JOIN
( SELECT User_ID,
RowNum,
@r2:= IF(@u2 = User_ID,@r2 + 1,1) AS RowNum2,
@u2:= User_ID
FROM ( SELECT DISTINCT p.User_ID, o.RowNum
FROM Photos AS p,
( SELECT @i:= @i + 1 AS RowNum
FROM INFORMATION_SCHEMA.COLLATION_CHARACTER_SET_APPLICABILITY,
( SELECT @i:= 0) AS i
) AS o
WHERE RowNum <= (SELECT COUNT(*) FROM Photos P1 WHERE p.User_ID = p1.User_ID)
AND NOT EXISTS
( SELECT 1
FROM Photos p2
WHERE p.User_ID = p2.User_ID
AND o.RowNum = p2.`Order`
)
AND p.`Order` IS NULL
ORDER BY User_ID, RowNum
) AS p,
(SELECT @r2:= 0) AS r,
(SELECT @u2:= 0) AS u
ORDER BY user_ID, RowNum
) AS numbers
ON Photos.User_ID = numbers.User_ID
AND photos.RowNum = numbers.RowNum2
ORDER BY User_ID, `Order`
但是,正如您所看到的,这非常复杂。这是通过将具有order
价值的人与没有价值的人分开对待而起作用的。order
最上面的查询只是按照每个用户的 ID 顺序排列所有没有值的照片。底部查询使用交叉连接为每个用户 ID 生成从 1 到 n 的顺序列表(最多为每个 User_ID 的条目数)。因此,使用这样的数据集:
ID User_ID Order
1 1 NULL
2 2 NULL
3 1 NULL
4 1 1
5 1 3
6 2 2
7 2 3
它会产生
UserID RowNum
1 1
1 2
1 3
1 4
2 1
2 2
2 3
然后,它使用NOT EXISTS
非 null 来消除 Photos 已经使用的所有组合order
,并按由 User_ID 划分的 RowNum 的顺序排列
UserID RowNum Rownum2
1 2 1
1 4 2
2 1 1
然后可以将 RowNum2 值与在 from 子查询中获得的 rownum 值匹配,从而给出正确的order
值。长篇大论,但它的工作原理。
SQL Fiddle 示例