我有两个问题。第一个查询:
select in_gentime
from in_time_temp
where cardnumber = 'MCL1570'
order by in_gentime
输出是:
2011-10-11 08:06:00.000
2011-10-12 08:35:00.000
2011-10-13 08:21:00.000
2011-10-15 08:21:00.000
2011-10-16 08:21:00.000
2011-10-17 08:21:00.000
2011-10-18 08:21:00.000
2011-10-19 08:21:00.000
2011-10-20 08:21:00.000
2011-10-21 08:21:00.000
2011-10-22 08:21:00.000
2011-10-24 08:21:00.000
2011-10-25 08:21:00.000
2011-10-26 09:00:00.000
2011-10-27 09:00:00.000
2011-10-28 09:00:00.000
2011-10-29 09:00:00.000
2011-10-31 09:00:00.000
第二个问题:
select out_gentime
from out_time_temp
where cardnumber = 'MCL1570'
order by out_gentime
输出是:
2011-10-11 22:02:00.000
2011-10-12 21:14:00.000
2011-10-14 21:59:00.000
2011-10-15 21:59:00.000
2011-10-16 21:59:00.000
2011-10-17 21:59:00.000
2011-10-18 21:59:00.000
2011-10-19 21:59:00.000
2011-10-20 21:59:00.000
2011-10-21 21:59:00.000
2011-10-22 21:59:00.000
2011-10-24 21:59:00.000
2011-10-25 21:59:00.000
2011-10-26 18:15:00.000
2011-10-27 18:15:00.000
2011-10-28 18:15:00.000
2011-10-29 23:15:00.000
2011-10-31 22:15:00.000
我需要识别出现在一个表中而不是另一个表中的DATE
值的记录。我想忽略具体的TIME
。例如,我想只返回这两条记录:
2011-10-13 08:21:00.000
2011-10-14 21:59:00.000
如何编写查询来执行此操作?
答案 0 :(得分:2)
select in_gentime as THETIME from in_time_temp where cardnumber = 'MCL1570'
and in_gentime not in
(select out_gentime from out_time_temp where cardnumber = 'MCL1570')
union
select out_gentime as THETIME from out_time_temp where cardnumber = 'MCL1570'
and out_gentime not in
(select in_gentime as THETIME from in_time_temp where cardnumber = 'MCL1570' )
order by THETIME
这应该为您提供两个表格中的所有唯一项目。
答案 1 :(得分:2)
如果您使用FULL OUTER JOIN
,则可以将日期列表连接在一起,然后只选择其中一个为NULL的记录:
SELECT COALESCE(i.in_gentime, o.out_gentime) -- pick first non-null value
FROM in_time_temp i
FULL OUTER JOIN out_time_temp o
ON CAST(CONVERT(varchar(8), i.in_gentime, 112) AS datetime) =
CAST(CONVERT(varchar(8), o.out_gentime, 112) AS datetime)
AND i.cardnumber = o.cardnumber
WHERE (i.in_gentime is null or o.out_gentime IS NULL)
AND (i.cardnumber = 'MCL1750' OR o.cardnumber = 'MCL1750')
<强>更新即可。 Nathan,这里是完整的测试代码,我不确定你为什么没有得到结果,但是当我运行它时会返回4条记录:
CREATE TABLE in_time_temp
(
in_gentime datetime,
cardnumber nvarchar(50)
)
insert into in_time_temp values('2011-10-11 08:06:00.000', 'MCL1750')
insert into in_time_temp values('2011-10-12 08:35:00.000', 'MCL1750')
insert into in_time_temp values('2011-10-13 08:21:00.000', 'MCL1750')
insert into in_time_temp values('2011-10-15 08:21:00.000', 'MCL1750')
insert into in_time_temp values('2011-10-16 08:21:00.000', 'MCL1750')
insert into in_time_temp values('2011-10-17 08:21:00.000', 'MCL1750')
CREATE TABLE out_time_temp
(
out_gentime datetime,
cardnumber nvarchar(50)
)
insert into out_time_temp values('2011-10-11 22:02:00.000', 'MCL1750')
insert into out_time_temp values('2011-10-12 21:14:00.000', 'MCL1750')
insert into out_time_temp values('2011-10-14 21:59:00.000', 'MCL1750')
insert into out_time_temp values('2011-10-15 21:59:00.000', 'MCL1750')
insert into out_time_temp values('2011-10-16 21:59:00.000', 'MCL1750')
insert into out_time_temp values('2011-10-17 21:59:00.000', 'MCL1750')
insert into out_time_temp values('2011-10-18 21:59:00.000', 'MCL1750')
insert into out_time_temp values('2011-10-19 21:59:00.000', 'MCL1750')
SELECT COALESCE(i.in_gentime, o.out_gentime) -- pick first non-null value
FROM in_time_temp i
FULL OUTER JOIN out_time_temp o
ON CAST(CONVERT(varchar(8), i.in_gentime, 112) AS datetime) =
CAST(CONVERT(varchar(8), o.out_gentime, 112) AS datetime)
AND i.cardnumber = o.cardnumber
WHERE (i.in_gentime is null or o.out_gentime IS NULL)
AND (i.cardnumber = 'MCL1750' OR o.cardnumber = 'MCL1750')
输出是:
2011-10-13 08:21:00.000
2011-10-14 21:59:00.000
2011-10-18 21:59:00.000
2011-10-19 21:59:00.000
答案 2 :(得分:1)
这应该为您提供两个表之一的时间:
SELECT CASE
WHEN in_gentime IS NOT NULL THEN in_gentime
ELSE out_gentime
END AS THETIME
FROM in_time_temp AS i
FULL OUTER JOIN out_time_temp AS out ON i.cardnumber = out.cardnumber
AND i.in_gentime = out.out_gentime
WHERE i.in_gentime IS NULL
OR out.i_gentime IS NULL
order by in_gentime
如果您只想引用DATE
而不是TIME
部分,那么答案就在这里(就像JohnD提供的那样,最大的区别在于我使用了CASE
和他(可能更有效率)使用COALESCE
)
SELECT CASE
WHEN i.in_gentime IS NOT NULL THEN i.in_gentime
ELSE o.out_gentime
END AS THETIME
FROM in_time_temp AS i
FULL OUTER JOIN out_time_temp AS o ON i.cardnumber = o.cardnumber
AND CAST(CONVERT(VARCHAR(8), i.in_gentime, 112) AS DATETIME) =
CAST(CONVERT(VARCHAR(8), o.out_gentime, 112) AS DATETIME)
WHERE i.in_gentime IS NULL
OR o.out_gentime IS NULL
order by i.in_gentime
答案 3 :(得分:0)
select in_gentime
from in_time_temp
where cardnumber = 'MCL1570' and
dateadd(day, datediff(day, 0, in_gentime), 0) not in
(select dateadd(day, datediff(day, 0, out_gentime), 0)
from out_time_temp
where cardnumber = 'MCL1570')
union all
select out_gentime
from out_time_temp
where cardnumber = 'MCL1570' and
dateadd(day, datediff(day, 0, out_gentime), 0) not in
(select dateadd(day, datediff(day, 0, in_gentime), 0)
from in_time_temp
where cardnumber = 'MCL1570')