วิธีการหาหรือ n สามTHเงินเดือนสูงสุดจากเงินเดือนtable(EmpID, EmpName, EmpSalary)
ในทางที่ดีที่สุด?
SELECT salary FROM (SELECT salary FROM employee ORDER BY salary DESC FETCH NEXT 3 ROWS ONLY) ORDER BY salary ASC FETCH NEXT 1 ROWS ONLY;
วิธีการหาหรือ n สามTHเงินเดือนสูงสุดจากเงินเดือนtable(EmpID, EmpName, EmpSalary)
ในทางที่ดีที่สุด?
SELECT salary FROM (SELECT salary FROM employee ORDER BY salary DESC FETCH NEXT 3 ROWS ONLY) ORDER BY salary ASC FETCH NEXT 1 ROWS ONLY;
คำตอบ:
ใช้ROW_NUMBER
(ถ้าคุณต้องการเดี่ยว) หรือDENSE_RANK
(สำหรับแถวที่เกี่ยวข้องทั้งหมด):
WITH CTE AS
(
SELECT EmpID, EmpName, EmpSalary,
RN = ROW_NUMBER() OVER (ORDER BY EmpSalary DESC)
FROM dbo.Salary
)
SELECT EmpID, EmpName, EmpSalary
FROM CTE
WHERE RN = @NthRow
EmpSalary
คอลัมน์ ยังลดลงเมื่อเทียบกับอะไร? ข้อได้เปรียบของวิธีการคือการที่คุณสามารถใช้ROW_NUMBER
..OVER(PARTITION BY GroupColumn OrderBy OrderColumn)
ดังนั้นคุณสามารถใช้เพื่อรับกลุ่ม แต่ยังเข้าถึงคอลัมน์ใดก็ได้
หมายเลขแถว:
SELECT Salary,EmpName
FROM
(
SELECT Salary,EmpName,ROW_NUMBER() OVER(ORDER BY Salary) As RowNum
FROM EMPLOYEE
) As A
WHERE A.RowNum IN (2,3)
แบบสอบถามย่อย:
SELECT *
FROM Employee Emp1
WHERE (N-1) = (
SELECT COUNT(DISTINCT(Emp2.Salary))
FROM Employee Emp2
WHERE Emp2.Salary > Emp1.Salary
)
คำหลักยอดนิยม:
SELECT TOP 1 salary
FROM (
SELECT DISTINCT TOP n salary
FROM employee
ORDER BY salary DESC
) a
ORDER BY salary
... WHERE (N-1) = (Subquery)...
ทำงาน แบบสอบถามย่อยเป็นแบบสอบถามที่สัมพันธ์กันเนื่องจากWHERE
ส่วนคำสั่งใช้Emp1
จากแบบสอบถามหลัก แบบสอบถามย่อยจะได้รับการประเมินทุกครั้งที่ข้อความค้นหาหลักสแกนในแถว ตัวอย่างเช่นถ้าเราจะหาเงินเดือนที่ใหญ่เป็นอันดับ 3 (N = 3) จาก (800, 1000, 700, 750) แบบสอบถามย่อยสำหรับแถวที่ 1 จะSELECT COUNT(DISTINCT(Emp2.Salary)) FROM Employee Emp2 WHERE Emp2.Salary > 800
เป็น 0 สำหรับค่าเงินเดือนที่ 4 (750) ... WHERE Emp2.Salary > 750
จะเป็น 2 หรือ N -1 ดังนั้นแถวนี้จะถูกส่งกลับ
ลองทำตามนี้
SELECT TOP 1 salary FROM (
SELECT TOP 3 salary
FROM employees
ORDER BY salary DESC) AS emp
ORDER BY salary ASC
สำหรับ 3 คุณสามารถแทนที่ค่าใดก็ได้ ...
หากคุณต้องการวิธีเพิ่มประสิทธิภาพให้ใช้TOP
Keyword ดังนั้นแบบสอบถามเงินเดือนสูงสุดและขั้นต่ำที่ n มีดังนี้ แต่แบบสอบถามดูเหมือนจะยุ่งยากเหมือนในลำดับย้อนกลับโดยใช้ชื่อฟังก์ชันรวม:
N เงินเดือนสูงสุด:
SELECT MIN(EmpSalary)
FROM Salary
WHERE EmpSalary IN(SELECT TOP N EmpSalary FROM Salary ORDER BY EmpSalary DESC)
สำหรับเงินเดือนสูงสุด 3 เท่า:
SELECT MIN(EmpSalary)
FROM Salary
WHERE EmpSalary IN(SELECT TOP 3 EmpSalary FROM Salary ORDER BY EmpSalary DESC)
N เงินเดือนขั้นต่ำ:
SELECT MAX(EmpSalary)
FROM Salary
WHERE EmpSalary IN(SELECT TOP N EmpSalary FROM Salary ORDER BY EmpSalary ASC)
สำหรับเงินเดือนขั้นต่ำ 3:
SELECT MAX(EmpSalary)
FROM Salary
WHERE EmpSalary IN(SELECT TOP 3 EmpSalary FROM Salary ORDER BY EmpSalary ASC)
ง่ายเกินไปถ้าคุณใช้แบบสอบถามย่อย!
SELECT MIN(EmpSalary) from (
SELECT EmpSalary from Employee ORDER BY EmpSalary DESC LIMIT 3
);
คุณสามารถเปลี่ยนค่าที่ n หลังข้อ จำกัด LIMIT ได้ที่นี่
ในนี้แบบสอบถามย่อยเลือก EmpSalary จากคำสั่งของพนักงานโดย EmpSalary DESC Limit 3; จะคืนเงินเดือน 3 อันดับแรกของพนักงาน จากผลลัพธ์เราจะเลือกเงินเดือนขั้นต่ำโดยใช้คำสั่ง MIN เพื่อรับเงินเดือน TOP อันดับ 3 ของพนักงาน
แทนที่ N ด้วย Max Number ของคุณ
SELECT *
FROM Employee Emp1
WHERE (N-1) = (
SELECT COUNT(DISTINCT(Emp2.Salary))
FROM Employee Emp2
WHERE Emp2.Salary > Emp1.Salary)
คำอธิบาย
แบบสอบถามด้านบนอาจทำให้สับสนได้หากคุณไม่เคยเห็นสิ่งใดมาก่อน - แบบสอบถามภายในคือสิ่งที่เรียกว่าแบบสอบถามย่อยที่สัมพันธ์กันเนื่องจากแบบสอบถามภายใน (แบบสอบถามย่อย) ใช้ค่าจากแบบสอบถามภายนอก (ในกรณีนี้คือตาราง Emp1 ) อยู่ในคำสั่ง WHERE
และSource
... WHERE (N-1) = (Subquery)...
ผล แบบสอบถามย่อยเป็นแบบสอบถามที่สัมพันธ์กันเนื่องจากWHERE
ส่วนคำสั่งใช้Emp1
จากแบบสอบถามหลัก แบบสอบถามย่อยจะได้รับการประเมินทุกครั้งที่ข้อความค้นหาหลักสแกนในแถว ตัวอย่างเช่นถ้าเราจะหาเงินเดือนที่ใหญ่เป็นอันดับ 3 (N = 3) จาก (800, 1000, 700, 750) แบบสอบถามย่อยสำหรับแถวที่ 1 จะSELECT COUNT(DISTINCT(Emp2.Salary)) FROM Employee Emp2 WHERE Emp2.Salary > 800
เป็น 0 สำหรับค่าเงินเดือนที่ 4 (750) ... WHERE Emp2.Salary > 750
จะเป็น 2 หรือ N -1 ดังนั้นแถวนี้จะถูกส่งกลับ
เงินเดือนสูงสุดที่สามหรือที่ n จากตารางเงินเดือนโดยไม่ต้องใช้แบบสอบถามย่อย
select salary from salary
ORDER BY salary DESC
OFFSET N-1 ROWS
FETCH NEXT 1 ROWS ONLY
สำหรับเงินเดือนสูงสุดอันดับ 3 ให้วาง 2 แทน N-1
SELECT Salary,EmpName
FROM
(
SELECT Salary,EmpName,DENSE_RANK() OVER(ORDER BY Salary DESC) Rno from EMPLOYEE
) tbl
WHERE Rno=3
SELECT EmpSalary
FROM salary_table
GROUP BY EmpSalary
ORDER BY EmpSalary DESC LIMIT n-1, 1;
อ้างถึงคำถามต่อไปนี้เพื่อรับเงินเดือนสูงสุดอันดับที่ n ด้วยวิธีนี้คุณจะได้รับเงินเดือนสูงสุดอันดับที่ n ใน MYSQL หากคุณต้องการได้รับเงินเดือนต่ำสุดอันดับที่ n คุณต้องแทนที่ DESC ด้วย ASC ในแบบสอบถาม
วิธีที่ 1:
SELECT TOP 1 salary FROM (
SELECT TOP 3 salary
FROM employees
ORDER BY salary DESC) AS emp
ORDER BY salary ASC
วิธีที่ 2:
Select EmpName,salary from
(
select EmpName,salary ,Row_Number() over(order by salary desc) as rowid
from EmpTbl)
as a where rowid=3
ในปี 2008 เราสามารถใช้ ROW_NUMBER () OVER (ORDER BY EmpSalary DESC) เพื่อรับอันดับที่ไม่มีความสัมพันธ์ที่เราสามารถใช้ได้
ตัวอย่างเช่นเราสามารถทำได้สูงสุดเป็นอันดับ 8 ด้วยวิธีนี้หรือเปลี่ยน @N เป็นอย่างอื่นหรือใช้เป็นพารามิเตอร์ในฟังก์ชันก็ได้หากต้องการ
DECLARE @N INT = 8;
WITH rankedSalaries AS
(
SELECT
EmpID
,EmpName
,EmpSalary,
,RN = ROW_NUMBER() OVER (ORDER BY EmpSalary DESC)
FROM salary
)
SELECT
EmpID
,EmpName
,EmpSalary
FROM rankedSalaries
WHERE RN = @N;
ใน SQL Server 2012 ดังที่คุณทราบว่าดำเนินการโดยสัญชาตญาณมากขึ้นโดยใช้ LAG ()
declare @maxNthSal as nvarchar(20)
SELECT TOP 3 @maxNthSal=GRN_NAME FROM GRN_HDR ORDER BY GRN_NAME DESC
print @maxNthSal
เพื่อให้ได้ค่าสูงสุดอันดับสามจากตาราง
SELECT * FROM tableName ORDER BY columnName DESC LIMIT 2, 1
นี่เป็นหนึ่งในคำถามยอดนิยมในการสัมภาษณ์ SQL ฉันจะเขียนแบบสอบถามต่างๆเพื่อหาค่าสูงสุดอันดับที่ n ของคอลัมน์
ฉันได้สร้างตารางชื่อ“ Emloyee” โดยเรียกใช้สคริปต์ด้านล่าง
CREATE TABLE Employee([Eid] [float] NULL,[Ename] [nvarchar](255) NULL,[Basic_Sal] [float] NULL)
ตอนนี้ฉันจะแทรก 8 แถวในตารางนี้โดยเรียกใช้คำสั่งแทรกด้านล่าง
insert into Employee values(1,'Neeraj',45000)
insert into Employee values(2,'Ankit',5000)
insert into Employee values(3,'Akshay',6000)
insert into Employee values(4,'Ramesh',7600)
insert into Employee values(5,'Vikas',4000)
insert into Employee values(7,'Neha',8500)
insert into Employee values(8,'Shivika',4500)
insert into Employee values(9,'Tarun',9500)
ตอนนี้เราจะพบ Basic_sal สูงสุดอันดับ 3 จากตารางด้านบนโดยใช้แบบสอบถามที่แตกต่างกัน ฉันเรียกใช้แบบสอบถามด้านล่างในสตูดิโอการจัดการและด้านล่างคือผลลัพธ์
select * from Employee order by Basic_Sal desc
เราจะเห็นในภาพด้านบนว่าเงินเดือนขั้นพื้นฐานสูงสุดอันดับ 3 จะเป็น 8500 ฉันกำลังเขียน 3 วิธีที่แตกต่างกันในการทำเช่นเดียวกัน เมื่อเรียกใช้แบบสอบถามทั้งสามที่กล่าวถึงด้านล่างเราจะได้ผลลัพธ์เดียวกันคือ 8500
วิธีแรก: - ใช้ฟังก์ชันหมายเลขแถว
select Ename,Basic_sal
from(
select Ename,Basic_Sal,ROW_NUMBER() over (order by Basic_Sal desc) as rowid from Employee
)A
where rowid=2
Select TOP 1 Salary as '3rd Highest Salary' from (SELECT DISTINCT TOP 3 Salary from Employee ORDER BY Salary DESC) a ORDER BY Salary ASC;
ฉันแสดงเงินเดือนสูงสุดเป็นอันดับ 3
SELECT MIN(COLUMN_NAME)
FROM (
SELECT DISTINCT TOP 3 COLUMN_NAME
FROM TABLE_NAME
ORDER BY
COLUMN_NAME DESC
) AS 'COLUMN_NAME'
- เงินเดือนสูงสุด
select *
from (select lstName, salary, row_number() over( order by salary desc) as rn
from employee) tmp
where rn = 2
- (ที่ n -1) เงินเดือนสูงสุด
select *
from employee e1
where 1 = (select count(distinct salary)
from employee e2
where e2.Salary > e1.Salary )
วิธีที่เพิ่มประสิทธิภาพ: แทนที่จะใช้คำค้นหาย่อยให้ใช้ขีด จำกัด
select distinct salary from employee order by salary desc limit nth, 1;
ดูลิมิตไวยากรณ์ที่นี่http://www.mysqltutorial.org/mysql-limit.aspx
ตามแบบสอบถามย่อย:
SELECT salary from
(SELECT rownum ID, EmpSalary salary from
(SELECT DISTINCT EmpSalary from salary_table order by EmpSalary DESC)
where ID = nth)
ลองใช้แบบสอบถามนี้
SELECT DISTINCT salary
FROM emp E WHERE
&no =(SELECT COUNT(DISTINCT salary)
FROM emp WHERE E.salary <= salary)
ใส่ n = ค่าที่คุณต้องการ
set @n = $n
SELECT a.* FROM ( select a.* , @rn = @rn+1 from EMPLOYEE order by a.EmpSalary desc ) As a where rn = @n
โซลูชันที่ทดสอบ MySQL สมมติว่า N = 4:
select min(CustomerID) from (SELECT distinct CustomerID FROM Customers order by CustomerID desc LIMIT 4) as A;
ตัวอย่างอื่น:
select min(country) from (SELECT distinct country FROM Customers order by country desc limit 3);
ลองใช้รหัสนี้: -
SELECT *
FROM one one1
WHERE ( n ) = ( SELECT COUNT( one2.salary )
FROM one one2
WHERE one2.salary >= one1.salary
)
ค้นหาเงินเดือนสูงสุด Nth จากตาราง นี่คือวิธีการทำงานนี้โดยใช้ฟังก์ชัน density_rank ()
select linkorder from u_links
select max(linkorder) from u_links
select max(linkorder) from u_links where linkorder < (select max(linkorder) from u_links)
select top 1 linkorder
from ( select distinct top 2 linkorder from u_links order by linkorder desc) tmp
order by linkorder asc
DENSE_RANK: 1. DENSE_RANK คำนวณอันดับของแถวในกลุ่มแถวที่เรียงลำดับและส่งกลับอันดับเป็น NUMBER อันดับคือจำนวนเต็มติดต่อกันที่ขึ้นต้นด้วย 1 2. ฟังก์ชันนี้ยอมรับอาร์กิวเมนต์เป็นชนิดข้อมูลตัวเลขและส่งกลับ NUMBER 3. ในฐานะฟังก์ชันการวิเคราะห์ DENSE_RANK จะคำนวณอันดับของแต่ละแถวที่ส่งคืนจากคิวรีเทียบกับแถวอื่น ๆ โดยอิงตามค่าของ value_exprs ใน order_by_clause 4. ในแบบสอบถามด้านบนอันดับจะถูกส่งกลับตาม sal ของตารางพนักงาน ในกรณีที่เสมอกันจะกำหนดอันดับที่เท่ากันให้กับทุกแถว
WITH result AS (
SELECT linkorder ,DENSE_RANK() OVER ( ORDER BY linkorder DESC ) AS DanseRank
FROM u_links )
SELECT TOP 1 linkorder FROM result WHERE DanseRank = 5
ใน SQL Server 2012+ OFFSET ... FETCH จะเป็นวิธีที่มีประสิทธิภาพในการบรรลุสิ่งนี้:
DECLARE @N AS INT;
SET @N = 3;
SELECT
EmpSalary
FROM
dbo.Salary
ORDER BY
EmpSalary DESC
OFFSET (@N-1) ROWS
FETCH NEXT 1 ROWS ONLY
select * from employee order by salary desc;
+------+------+------+-----------+
| id | name | age | salary |
+------+------+------+-----------+
| 5 | AJ | 20 | 100000.00 |
| 4 | Ajay | 25 | 80000.00 |
| 2 | ASM | 28 | 50000.00 |
| 3 | AM | 22 | 50000.00 |
| 1 | AJ | 24 | 30000.00 |
| 6 | Riu | 20 | 20000.00 |
+------+------+------+-----------+
select distinct salary from employee e1 where (n) = (select count( distinct(salary) ) from employee e2 where e1.salary<=e2.salary);
แทนที่ n ด้วยเงินเดือนสูงสุดอันดับที่ n เป็นตัวเลข
SELECT TOP 1 salary FROM ( SELECT TOP n salary FROM employees ORDER BY salary DESC Group By salary ) AS emp ORDER BY salary ASC
(โดยที่ n สำหรับเงินเดือนสูงสุดที่ n)
เพียงแค่เปลี่ยนค่าแบบสอบถามภายในเช่นเลือกด้านบน (2) * จากลำดับ Student_Info ตาม ClassID desc
ใช้สำหรับปัญหาทั้งสอง:
Select Top (1)* from
(
Select Top (1)* from Student_Info order by ClassID desc
) as wsdwe
order by ClassID
การสอบถามnth highest bonus
การพูดn=10
โดยใช้ AdventureWorks2012 ลองรหัสต่อไปนี้
USE AdventureWorks2012;
GO
SELECT * FROM Sales.SalesPerson;
GO
DECLARE @grade INT;
SET @grade = 10;
SELECT MIN(Bonus)
FROM (SELECT TOP (@grade) Bonus FROM (SELECT DISTINCT(Bonus) FROM Sales.SalesPerson) AS a ORDER BY Bonus DESC) AS g