我有一张类似
的表格EMPLOYEE_ID DTL_ID COLUMN_A COLUMN_B
---------------------------
JOHN 0 1 1
JOHN 1 3 1
LINN 0 1 12
SMITH 0 9 1
SMITH 1 11 12
这意味着每个人都会有一个或多个具有不同DTL_ID
值的记录(0,1,2 ......等)。
现在我想创建一个T-SQL语句来检索EMPLOYEE_ID
和DTL_ID
的记录。
如果找不到指定的DTL_ID
,将返回DTL_ID=0
的记录。
我知道我可以通过各种方式实现这一目标,例如首先通过EXISTS
或COUNT(*)
检查行是否存在,然后检索该行。
但是,我想知道其他可能的方法,因为这个检索语句在我的应用程序中很常见,而且我的表有十万行。
在上面的方法中,即使指定了DTL_ID
的记录存在,我也必须检索两次,我想避免这种情况。
答案 0 :(得分:2)
像这样:
SELECT *
FROM table
WHERE EMPLOYEE_ID = ?? AND DTL_ID = ??
UNION
SELECT *
FROM table
WHERE EMPLOYEE_ID = ?? AND DTL_ID = 0
AND NOT EXISTS (SELECT *
FROM table
WHERE EMPLOYEE_ID = ?? AND DTL_ID = ??)
你当然要填写?用正确的数字。
答案 1 :(得分:2)
如果DTL_ID始终为0或正数:
SELECT TOP 1 * FROM table
where EmployeeID = @EmployeeID and DTL_ID in (@DTL_ID,0)
order by DTL_ID desc
如果您在单个查询等中跨多个员工工作,那么如果您的SQL版本支持,您可能希望使用ROW_NUMBER()。
答案 2 :(得分:0)
在最终的ISNULL(DTL_ID, 0)
查询中使用SELECT
答案 3 :(得分:0)
SELECT E1.EMPLOYEE_ID, ISNULL(E2.DTL_ID, 0), E1.COLUMN_A, E1.COLUMN_B EMPLIYEES AS E1
LEFT JOIN EMPLIYEES AS E2
ON E1.EMPLOYEE_ID = E2.EMPLOYEE_ID AND E2.DTL_ID = 42
答案 4 :(得分:0)
SELECT MAX(DTL_ID) ...
WHERE DTL_ID IN (@DTL_ID, 0)
答案 5 :(得分:0)
您可以使用top
和union
,例如:
declare @t table(id int, value int, c char)
insert @t values (1,0,'a'), (1,1,'b'), (1,2,'c')
declare @id int = 1;
declare @value int = 2;
select top(1) *
from
(
select *
from @t t
where t.value = @value and t.id = @id
union all
select *
from @t t
where t.value = 0
)a
order by a.value desc
如果@value = 2
比查询返回1 2 c
。如果@value = 3
比查询返回1 0 a
。