我所擁有的是MS-SQL數據庫,用於存儲來自安裝在某些車輛(每車1-3輛設備)的設備的數據/信息。如何使用邏輯條件在現有表上創建查詢並使用bool數據構建表(視圖)?
目前,數據庫中有一張名爲Communication
的表 - 用於存儲設備連接到TCP服務器時每個信息的大表。記錄一個接一個地添加(僅在這裏插入)。
表看起來是這樣的:
我需要的是一個SQL
查詢(指令/語句)爲所謂的「每週通訊狀態」創建表(視圖),其中我可以看到是否/如何在汽車在過去的7天已通知...像下表:
我所擁有的是MS-SQL數據庫,用於存儲來自安裝在某些車輛(每車1-3輛設備)的設備的數據/信息。如何使用邏輯條件在現有表上創建查詢並使用bool數據構建表(視圖)?
目前,數據庫中有一張名爲Communication
的表 - 用於存儲設備連接到TCP服務器時每個信息的大表。記錄一個接一個地添加(僅在這裏插入)。
表看起來是這樣的:
我需要的是一個SQL
查詢(指令/語句)爲所謂的「每週通訊狀態」創建表(視圖),其中我可以看到是否/如何在汽車在過去的7天已通知...像下表:
作爲替代上面,給,你知道會有在輸出中只有7個日期列可以執行手動操作,而不是使用PIVOT操作符。
select VehicleNumber,
CASE WHEN SUM(CASE WHEN DATEDIFF(d,DateTimeCommunication, DATEADD(d,-7,GETDATE())) = 0 THEN 1 ELSE 0 END) > 0 THEN 'YES' Else 'NO' END AS [7 Days Ago]
,CASE WHEN SUM(CASE WHEN DATEDIFF(d,DateTimeCommunication, DATEADD(d,-6,GETDATE())) = 0 THEN 1 ELSE 0 END) > 0 THEN 'YES' Else 'NO' END AS [6 Days Ago]
,CASE WHEN SUM(CASE WHEN DATEDIFF(d,DateTimeCommunication, DATEADD(d,-5,GETDATE())) = 0 THEN 1 ELSE 0 END) > 0 THEN 'YES' Else 'NO' END AS [5 Days Ago]
,CASE WHEN SUM(CASE WHEN DATEDIFF(d,DateTimeCommunication, DATEADD(d,-4,GETDATE())) = 0 THEN 1 ELSE 0 END) > 0 THEN 'YES' Else 'NO' END AS [4 Days Ago]
,CASE WHEN SUM(CASE WHEN DATEDIFF(d,DateTimeCommunication, DATEADD(d,-3,GETDATE())) = 0 THEN 1 ELSE 0 END) > 0 THEN 'YES' Else 'NO' END AS [3 Days Ago]
,CASE WHEN SUM(CASE WHEN DATEDIFF(d,DateTimeCommunication, DATEADD(d,-2,GETDATE())) = 0 THEN 1 ELSE 0 END) > 0 THEN 'YES' Else 'NO' END AS [2 Days Ago]
,CASE WHEN SUM(CASE WHEN DATEDIFF(d,DateTimeCommunication, DATEADD(d,-1,GETDATE())) = 0 THEN 1 ELSE 0 END) > 0 THEN 'YES' Else 'NO' END AS [1 Days Ago]
,CASE WHEN SUM(CASE WHEN DATEDIFF(d,DateTimeCommunication, GETDATE()) = 0 THEN 1 ELSE 0 END) > 0 THEN 'YES' Else 'NO' END AS [0 Days Ago]
from Communications
GROUP BY VehicleNumber
@groenhen你會注意到Sum函數包裝每一行。因爲我們將車輛編號I.E.每一行顯示單個車輛,所有其他顯示的數據彙總。在這種情況下,聚合是爲單個車輛拍攝行並將它們壓在一起。然後,每次我們有匹配的日期時,總和函數就會有效計數。因此,在該行的末尾,我們會說,如果這個計數> 0,那麼'是'。所以,因爲這是使用group by,我們需要使用一個聚合函數,因此我們需要做所有額外的工作。在我看來更容易閱讀。好 ? – sarin
謝謝沙林。我剛剛在提出這個問題後立即想到了,可能我太累了,因爲我在第一次閱讀時沒有注意到SUM ...那爲什麼我刪除了評論。但你的回答是非常受歡迎的,因爲它總是有好的確認:) –
@groenhen沒有問題。隨時標記它是正確的,upvote,如果它是有幫助的! – sarin
這裏是一個動態的PIVOT
的方法。
CREATE TABLE #temp(equipmentID int, vehicleNumber int, DateTimeCommunication datetime)
INSERT INTO #temp(equipmentID, vehicleNumber, DateTimeCommunication)
VALUES (1,100,GETDATE()),
(2,110,GETDATE()),
(3,120,GETDATE()),
(5,140,GETDATE()),
(1,100,DATEADD(day,-8,GETDATE())),
(3,120,DATEADD(day,-8,GETDATE())),
(4,130,DATEADD(day,-8,GETDATE())),
(5,140,DATEADD(day,-8,GETDATE()))
DECLARE @sql nvarchar(max), @columns nvarchar(max), @columnsSelect nvarchar(max)
SELECT @columns = COALESCE(@columns + N',['+CONVERT(nvarchar(max),dateCom)+N']',N'['+CONVERT(nvarchar(max),dateCom)+N']')
FROM (
SELECT DISTINCT CONVERT(date, DateTimeCommunication) as dateCom
FROM #temp
) as allDates
ORDER BY dateCom
SELECT @columnsSelect = COALESCE(@columnsSelect + N',ISNULL(['+CONVERT(nvarchar(max),dateCom)+N'],N''NO'') as '''+CONVERT(nvarchar(max),dateCom)+'''',
N'ISNULL(['+CONVERT(nvarchar(max),dateCom)+N'],N''NO'') as '''+CONVERT(nvarchar(max),dateCom)+'''')
FROM (
SELECT DISTINCT CONVERT(date, DateTimeCommunication) as dateCom
FROM #temp
) as allDates
ORDER BY dateCom
SET @sql = N'SELECT pvt.vehicleNumber, '[email protected]+'
FROM (
SELECT t.equipmentID, t.vehicleNumber, CONVERT(date,DateTimeCommunication) as dateCom,
CASE WHEN t.DateTimeCommunication BETWEEN DATEADD(day,-7,GETDATE()) AND GETDATE()
THEN N''YES''
ELSE N''NO''
END as communicated
FROM #temp t
) as dat
PIVOT(
MAX(communicated)
FOR dateCom IN('[email protected]+')
) as pvt'
PRINT(@sql)
EXEC (@sql)
DROP TABLE #temp
如果你不需要它的動態或只爲指定日期範圍內,只需再次簡化了它這樣的:
CREATE TABLE #temp(equipmentID int, vehicleNumber int, DateTimeCommunication datetime)
INSERT INTO #temp(equipmentID, vehicleNumber, DateTimeCommunication)
VALUES (1,100,GETDATE()),
(2,110,GETDATE()),
(3,120,GETDATE()),
(5,140,GETDATE()),
(1,100,DATEADD(day,-8,GETDATE())),
(3,120,DATEADD(day,-8,GETDATE())),
(4,130,DATEADD(day,-8,GETDATE())),
(5,140,DATEADD(day,-8,GETDATE()))
SELECT *
FROM (
SELECT t.equipmentID, t.vehicleNumber, CONVERT(date,DateTimeCommunication) as dateCom,
CASE WHEN t.DateTimeCommunication BETWEEN DATEADD(day,-7,GETDATE()) AND GETDATE()
THEN N'YES'
ELSE N'NO'
END as communicated
FROM #temp t
) as dat
PIVOT(
MAX(communicated)
FOR dateCom IN([2015-06-23]) --needs to be changed on different date!
) as pvt
DROP TABLE #temp
我一定會努力的第二個方法的明天。現在/這裏我沒有SQL服務器,所以... :)非常感謝,喬佩它會工作:) –
沒問題。只要告訴我它是不是你想要的東西。但所有的工作在我的機器上。 – Ionic
使用轉動命令 – Smart003