2015-12-30 96 views
2

我有这样的桌子;按升序排列选择的列

Reg_No  Student_Name   col1 col2 col3 
----------- -------------------- ------ ------ ------ 
101   Kevin    77   94   78 
102   Andrew    91   81   17 
103   Scott    46   83   28 

我怎么能选择COL1,COL2,COL3和COL1,COL2,COL3这些选择的值安排成从各行按升序排列,但保留在该表被访问,因此看起来顺序如下所示?

Reg_No  Student_Name   Lowest Middle Highest 
----------- ------------------- --------- --------- --------- 
101   Kevin    77   78   94 
102   Andrew    17   81   91 
103   Scott    28   46   83 

我使用MSSQL Server 2008 R2的

+0

关系数据库不以这种方式工作,可以在SQL中实现,虽然,但我建议你要么储存过程中或最终输出 –

+0

订购过程中做到这一点是柱状操作。我不认为有一种直接的方法可以做你想问的问题 –

回答

3

这是SQL Server之类的痛苦。一种方法是不转发数据,然后重新转发。我会倾向于做这个使用条件汇总:

select Reg_No, Student_Name, 
     max(case when seqnum = 1 then col end) as Lowest, 
     max(case when seqnum = 2 then col end) as Middle, 
     max(case when seqnum = 3 then col end) as Highest 
from (select t.*, v.col, 
      row_number() over (partition by Reg_No, Student_Name order by v.col) as seqnum 
     from likethis t cross apply 
      (values (t.col1), (t.col2), (t.col3) 
      ) v(col) 
    ) t 
group by Reg_No, Student_Name; 

如果试图用case语句来做到这一点,他们就会变得非常复杂,因为可能的联系和NULL值。

0

你需要将资料标准化,但直到然后:

with temp (ColNo, Reg_No, Student_Name, col) as 
    select 1, Reg_No, Student_Name, col1 
    from Students 
    union all 
    select 2, Reg_No, Student_Name, col2 
    from Students 
    union all 
    select 3, Reg_No, Student_Name, col3 
    from Students; 


select 
    min(t1.col) as Lowest, 
    max(t2.col) as Middle 
    max(t1.col) as Highest 
from temp t1 
join t2 
on t1.Reg_No = t2.Reg_No 
    and t1.Student_Name = t1.Student_Name 
    and t1.ColNo <> t2.ColNo -- don't match on self 
    and t1.col >= t2.col  -- don't include the max in t2 unless more than 1 
group by t1.Reg_No, t1.Student_Name 
order by t1.Reg_No, t1.Student_Name 

因此,如果一套(COL1,COL2,COL3)是(1,2,3)然后T2结束是(1 ,2),最大其中是2

如果设定为(3,3,1),然后T2结束是(3,3,1),最大一个被3.

0

这里是一种没有生成的方式Row_Number

WITH cte 
    AS (SELECT reg_no, 
       student_name, 
       Max(v.col)OVER(partition BY reg_no, student_name) AS highest, 
       Min(v.col)OVER(partition BY reg_no, student_name) AS lowest, 
       col 
     FROM Yourtable t 
       CROSS apply (VALUES (t.col1),(t.col2),(t.col3)) v(col)) 
SELECT reg_no, 
     student_name, 
     lowest=Min(lowest), 
     Middle=Min(CASE WHEN col <> lowest AND col <> highest THEN col END), 
     highest=Max(highest) 
FROM cte 
GROUP BY reg_no, 
      student_name