Aynı sorguda farklı parametrelerle iki kez bir TVF'yi aramaya çalışıyorum, ancak bazı nedenlerle, sonuçlara birlikte katıldığımda, sonuçlardan biri Öbür maskeler diğeri. Ben bu küçük örneğe sorunumu aşağı düşürdük:Hatalı sonuçlar gösteren ayrı CTE'lerde farklı parametreler içeren çok bildirimli TVF çağrısı
CREATE FUNCTION dbo.fnTestErrorInline(@Test INT)
RETURNS TABLE
AS
RETURN
(
SELECT ID, Val
FROM (VALUES
(1, 1, 10),
(1, 2, 20),
(1, 3, 30),
(1, 4, 40),
(2, 1, 50),
(2, 2, 60),
(2, 3, 70),
(2, 4, 80)
) t(Test, ID, Val)
WHERE [email protected]
)
ve bir eşdeğer satırlı fonksiyonu:
bu satır içi TVF al
CREATE FUNCTION dbo.fnTestErrorMultiline(@Test INT)
RETURNS @tbl TABLE (
ID INT NOT NULL,
Val INT NOT NULL
)
AS
BEGIN
IF @Test=1
INSERT INTO @tbl (ID, Val) VALUES
(1, 10),
(2, 20),
(3, 30),
(4, 40);
IF @Test=2
INSERT INTO @tbl (ID, Val) VALUES
(1, 50),
(2, 60),
(3, 70),
(4, 80);
RETURN
END
ben bu sorguyu çalıştırırsanız:
WITH cte1 AS (
SELECT ID, SUM(Val) AS Total
FROM dbo.fnTestErrorInline(1)
GROUP BY ID
), cte2 AS (
SELECT ID, SUM(Val) AS Total
FROM dbo.fnTestErrorInline(2)
GROUP BY ID
)
SELECT *
FROM cte1 c1
INNER JOIN cte2 c2 ON c1.ID=c2.ID;
sonuçlar beklendiği gibi olur:
ID Total ID Total
1 10 1 50
2 20 2 60
3 30 3 70
4 40 4 80
ama fonksiyonun satırlı sürümünü kullandığınızda:
WITH cte1 AS (
SELECT ID, SUM(Val) AS Total
FROM dbo.fnTestErrorMultiline(1)
GROUP BY ID
), cte2 AS (
SELECT ID, SUM(Val) AS Total
FROM dbo.fnTestErrorMultiline(2)
GROUP BY ID
)
SELECT *
FROM cte1 c1
INNER JOIN cte2 c2 ON c1.ID=c2.ID;
sonuç yanlıştır - cte2 cte1 aynı değerleri gösterir: Ayrıca
ID Total ID Total
1 10 1 10
2 20 2 20
3 30 3 30
4 40 4 40
, sadece bu davranışı görmek GROUP BY
mevcut olduğunda. Bu olmadan, sonuçlar iyi.
WITH cte1 AS (
SELECT ID, SUM(Val) AS Total
FROM dbo.fnTestErrorMultiline(1)
GROUP BY ID
), cte2 AS (
SELECT ID, SUM(Val) AS Total, SUM(Val+0) AS why
FROM dbo.fnTestErrorMultiline(2)
GROUP BY ID
)
SELECT *
FROM cte1 c1
INNER JOIN cte2 c2 ON c1.ID=c2.ID;
Ekstra sütun TVF tablodaki bir sütuna başvuru gerekiyor görünür
ID Total ID Total why
1 50 1 50 50
2 60 2 60 60
3 70 3 70 70
4 80 4 80 80
verir: Ben ikinci CTE için başka bir sütun eklerseniz
Garip bir şekilde, bu sonuçları değiştirir - Sabit bir değer, sonuçları değiştirmez.
Neler oluyor burda? Çok satırlı bir TVF'i sorgu başına birden çok kez çağırmamanız mı gerekiyor?
ben SQL Server 2008 R2 ve bu test ettik 2012
hala sonuçları görebilirsiniz ikinci CTE fnTestErrorMultiline' '3 ila geçirerek. http://sqlfiddle.com/#!6/e0395/13. Garip olan –
@ MM93 tuhaf! Bu, ikinci CTE'nin katılacağı herhangi bir satır olmayacağından, fonksiyonun sadece bir kez çalıştığını ima ettiği görülüyor. Sorgu planına bakıldığında, 'Tablo Değerli Fonksiyonu' iki kez göründüğünden, gerçekten ne olduğunu bilmiyorum – David
Siparişi değiştirirseniz (yani) ilk CTE'de '3''ü' fnTestErrorMultiline'yi geçersem sonuçları göremiyorum –