如何按列和下一行排序并按其他列排序?

时间:2018-02-02 17:13:04

标签: sql sql-server sorting sql-order-by

我有一个包含四列的表:IDisErrorSolidLineHighestError

每行与SolidLine列的另一行相关。所以我们在表中有两个相关的行。

例如,ID 1和2的行与SolidLine(5)有关系。

----------------------------------------------------------------------
|      ID      |    isError     |      SolidLine   |    HighestError
----------------------------------------------------------------------
|       1      |     0          |        5         |     1
|       2      |     0          |        5         |     1
|       3      |     0          |        8         |     1
|       4      |     0          |        8         |     1
|       5      |     1          |        10        |     50 
|       6      |     0          |        10        |     1
|       7      |     1          |        4         |     80
|       8      |     0          |        4         |     1
|       9      |     1          |        7         |     80
|      10      |     0          |        7         |     1
|      11      |     0          |        3         |     1 
|      12      |     0          |        3         |     1
----------------------------------------------------------------------

我想按以下条件对表格进行排序:

  

如果isError为1,请按SolidLine的下一行,然后按顺序排序   HighestError

所以希望结果应如下所示:

----------------------------------------------------------------------
|      ID      |    isError     |      SolidLine   |    HighestError
----------------------------------------------------------------------
|       7      |     1          |        4         |   80
|       8      |     0          |        4         |   1
|       9      |     1          |        7         |   80
|       10     |     0          |        7         |   1
|       5      |     1          |        10        |   50
|       6      |     0          |        10        |   1
|       1      |     0          |        5         |   1
|       2      |     0          |        5         |   1
|       3      |     0          |        8         |   1
|       4      |     0          |        8         |   1
|       11     |     0          |        3         |   1
|       12     |     0          |        3         |   1 
----------------------------------------------------------------------

第一行成为第一行,因为HighestErrorisError中的最大值等于1.然后下一行ID = 8,因为它{{ 1}}具有SolidLine = 7的行的SolidLine值。

ID总是在一起,并且不依赖于SolidLine列。

因此isError绑定的行对应始终在一起。

我尝试了以下查询,但结果错误:

SolidLine

--it breaks SolidLine ordering. 
SELECT ID, isError, SolidLine, HighestError
FROM SolidThreads
ORDER BY SolidLine, isError, HighestError desc, id

我做错了什么?或者我该怎么做?

3 个答案:

答案 0 :(得分:2)

正如你所描述的那样,你应该可以通过......来实现这个目标。

  • 为&#34添加一列;此实线包含错误行"
  • 为&#34添加一列;此实线"
  • 的最大错误
  • 使用CASE表达式根据错误状态更改排序

http://sqlfiddle.com/#!18/84e7a/1

WITH
  SolidThreadsSummary AS
(
  SELECT
    *,
    MAX(isError     ) OVER (PARTITION BY SolidLine)   AS SolidLineHasError,
    MAX(highestError) OVER (PARTITION BY SolidLine)   AS SolidLineMaxError
  FROM
    SolidThreads
)
SELECT
  *
FROM
  SolidThreadsSummary
ORDER BY
  SolidLineHasError DESC,  -- Not really necessary for your data
  SolidLineMaxError DESC,
  CASE WHEN SolidLineHasError > 0 THEN SolidLine ELSE 1 END,
  isError DESC,
  id


如果对并不总是按id连续(对于不包含错误的对),这可能会更加健壮......

http://sqlfiddle.com/#!18/84e7a/2

WITH
  SolidThreadsSummary AS
(
  SELECT
    *,
    MAX(isError     ) OVER (PARTITION BY SolidLine)   AS SolidLineHasError,
    MAX(highestError) OVER (PARTITION BY SolidLine)   AS SolidLineMaxError,
    MIN(id          ) OVER (PARTITION BY SolidLine)   AS SolidLineMinID
  FROM
    SolidThreads
)
SELECT
  *
FROM
  SolidThreadsSummary
ORDER BY
  SolidLineHasError DESC,
  SolidLineMaxError DESC,
  CASE WHEN SolidLineHasError > 0 THEN SolidLine ELSE 1 END,
  isError DESC,
  SolidLineMinID,
  id
;

答案 1 :(得分:1)

似乎您想要将SolidLines保持在一起排序,并先按HighestError排序这些组,然后按组中的最低ID排序,然后在组中首先显示错误。假设这是你想要的,我会用派生表来做这个:

ID, isError, SolidLine, HighestError
FROM SolidThreads INNER JOIN
(SELECT SolidLine, MAX(Highesterror) as sorting_HighestError, MIN(ID) as Sorting_Id
    FROM SolidThreads GROUP BY SolidLine) as Sorting_DT
ON Sorting_DT.SolidLine = SolidThreads.SolidLine
ORDER BY sorting_HighestError DESC, Sorting_Id, isError Desc, Id

答案 2 :(得分:1)

如果每个ID对的SolidLine始终是连续的,您只需执行this

SELECT T.*
FROM yourTable T
JOIN (SELECT SolidLine, MAX(HighestError) MaxError
      FROM yourTable
      GROUP BY SolidLine) T2 ON T.SolidLine = T2.SolidLine
ORDER BY MaxError DESC, ID