我有一个SelfJoin查询
;WITH t as
(
SELECT
ROW_NUMBER() OVER (ORDER BY dbo.DIM_PROJECT_TECH_OBJ.FUNCTIONAL_LOCATION,DATEADD(ms, DATEDIFF(ms, '00:00:00', CONVERT(VARCHAR,REPLACE(dbo.FACT_MEASUREMENT.Doc_Time,'24:00:00','23:59:59'),102)), CONVERT(DATETIME, dbo.DIM_TIME_USAGE.DATE)) ASC) AS Rowy,
dbo.FACT_MEASUREMENT.FACT_MEASUREMENT_KEY,
dbo.FACT_MEASUREMENT.Doc_Number,
dbo.FACT_MEASUREMENT.Created_By,
dbo.FACT_MEASUREMENT.Text,
dbo.FACT_MEASUREMENT.Doc_Time,
dbo.FACT_MEASUREMENT.Date_Loaded,
dbo.DIM_VC_MEASURE.VALUATION_CODE_AND_DESC,
dbo.DIM_TIME_USAGE.DATE,
dbo.DIM_PROJECT_TECH_OBJ.FUNCTIONAL_LOCATION,
dbo.DIM_VC_MEASURE.VALUATION_CODE,
CONVERT(VARCHAR,REPLACE(dbo.FACT_MEASUREMENT.Doc_Time,'24:00:00','23:59:59'),102) AS TIME,
DATEADD(ms, DATEDIFF(ms, '00:00:00', CONVERT(VARCHAR,REPLACE(dbo.FACT_MEASUREMENT.Doc_Time,'24:00:00','23:59:59'),102)), CONVERT(DATETIME, dbo.DIM_TIME_USAGE.DATE)) AS DATUM
FROM
dbo.DIM_PROJECT_TECH_OBJ INNER JOIN dbo.FACT_MEASUREMENT ON (dbo.FACT_MEASUREMENT.PROJECT_TECH_OBJ_KEY=dbo.DIM_PROJECT_TECH_OBJ.PROJECT_TECH_OBJ_KEY)
INNER JOIN dbo.DIM_TIME_USAGE ON (dbo.FACT_MEASUREMENT.TIME_KEY=dbo.DIM_TIME_USAGE.TIME_KEY)
INNER JOIN dbo.DIM_VC_MEASURE ON (dbo.DIM_VC_MEASURE.VALUATION_CODE_KEY=dbo.FACT_MEASUREMENT.VALUATION_CODE_KEY)
WHERE
dbo.FACT_MEASUREMENT.Measurement_Position = 'AVAILABILITY'
AND
dbo.DIM_PROJECT_TECH_OBJ.FUNCTIONAL_LOCATION IN ('XXX','YYY','ZZZ')
)
select t.*, tprev.DATUM AS PRE_DATUM, tprev.VALUATION_CODE AS PRE_CODE, DATEDIFF (minute,tprev.DATUM, t.DATUM) AS DELTA_MIN
from t join
t tprev
on tprev.rowy = t.rowy - 1 AND tprev.FUNCTIONAL_LOCATION = t.FUNCTIONAL_LOCATION ;
这将返回一组字段
FUNTIONAL LOC DATUM CODE PRE_DATUM PRE_CODE (-> Other fields)
XXX 01/07/2015 A 06/06/2015 Y
XXX 05/07/2015 B 01/07/2015 A
XXX 10/07/2015 C 05/07/2015 B
YYY 03/07/2015 B 15/06/2015 K
YYY 09/07/2015 C 03/07/2015 B
YYY 15/07/2015 A 09/07/2015 C
现在我想创建一个带有日历(图像从01/07到10/07)日期的外部联接,并获得类似的内容:
FUNTIONAL LOC DATUM CODE PRE_DATUM PRE_CODE
XXX 01/07/2015 A 06/06/2015 Y
XXX 02/07/2015 06/06/2015 Y
XXX 03/07/2015 06/06/2015 Y
XXX 04/07/2015 06/06/2015 Y
XXX 05/07/2015 B 01/07/2015 A
XXX 06/07/2015 01/07/2015 A
XXX 07/07/2015 01/07/2015 A
XXX 08/07/2015 01/07/2015 A
XXX 09/07/2015 01/07/2015 A
XXX 10/07/2015 C 05/07/2015 B
YYY 01/07/2015 15/06/2015 K
YYY 02/07/2015 15/06/2015 K
YYY 03/07/2015 B 15/06/2015 K
YYY 09/07/2015 C 03/07/2015 B
YYY 10/07/2015 03/07/2015 B
基本上,如果在日历数据上找不到代码,请使用prev。
有任何建议/想法吗? 提前谢谢。
S上。
答案 0 :(得分:1)
您需要使用cross join
表格calender
查询结果。像这样的东西
WITH t
AS (SELECT Row_number()
OVER (
ORDER BY Q2.FUNCTIONAL_LOCATION) AS Rowy,
Q1.FACT_MEASUREMENT_KEY,
CONVERT(VARCHAR(255), Q1.Doc_Time, 102) AS TIME
FROM dbo.DIM_PROJECT_TECH_OBJ Q2
INNER JOIN dbo.FACT_MEASUREMENT Q1
ON Q1.PROJECT_TECH_OBJ_KEY = Q2.PROJECT_TECH_OBJ_KEY
WHERE Q1.Measurement_Position = 'XXX'),
result
AS (SELECT t.*,
tprev.time
FROM t
LEFT JOIN t tprev
ON tprev.rowy = t.rowy - 1),
date_cook
AS (SELECT FUNTIONAL_LOC,
c.dates,
PRE_DATUM,
PRE_CODE
FROM result r
CROSS JOIN calender c
WHERE c.dates BETWEEN '2015-07-01' AND '2015-07-10')
SELECT dc.FUNTIONAL_LOC,
dc.dates AS DATUM,
Isnull(r.code, '') AS code,
dc.PRE_DATUM,
dc.PRE_CODE
FROM date_cook dc
LEFT OUTER JOIN result r
ON dc.FUNTIONAL_LOC= r.FUNTIONAL_LOC
AND dc.dates = r.DATUM
AND dc.PRE_DATUM = r.PRE_DATUM
AND dc.PRE_CODE = r.PRE_CODE
答案 1 :(得分:1)
您可以尝试以下步骤:
WITH
语句LEFT JOIN
和上面定义的中间结果(某些数据库需要指定LEFT OUTER JOIN
)前两个步骤的示例:
WITH t as ( ... ),
t2 as ( select t.*, tprev.time
from t left join
t tprev
on tprev.rowy = t.rowy - 1 ),
cal as ( ... )
SELECT *
FROM cal
LEFT JOIN t2
ON cal.DATUM = t2.DATUM;
请注意:
t2
希望这有帮助!
答案 2 :(得分:0)
我通过创建LEFT JOIN(日历记录到结果记录)来管理:在这种情况下,我正在避免通过CROSS连接获得的笛卡尔积,并且所有产品都是重复的。 对于PRE-CODE,我想在Result表上使用自联接:
WITH t as (
SELECT ROW_NUMBER() OVER (ORDER BY Q2.FUNCTIONAL_LOCATION) AS Rowy,
Q1.FACT_MEASUREMENT_KEY,
CONVERT(VARCHAR(255), Q1.Doc_Time, 102) AS TIME
FROM dbo.DIM_PROJECT_TECH_OBJ Q2 INNER JOIN
dbo.FACT_MEASUREMENT Q1
ON Q1.PROJECT_TECH_OBJ_KEY = Q2.PROJECT_TECH_OBJ_KEY
WHERE Q1.Measurement_Position = 'XXX'
)
select t.*, tprev.time
from t left join
t tprev
on tprev.rowy = t.rowy - 1;