2016-05-30 87 views
2

如果那個標題不代表我的問題在這裏,我很抱歉。在sql server 2008中的SQL FIFO邏輯

我有表1與多個項目。

表1

|No|Item|Quantity X|  
|1 |A |20  | 
|2 |A |21  | 
|3 |A |10  | 
|4 |B |3   | 
|5 |B |4   | 
... 

項目A我定製的FIFO功能結果:

|No|Name  |Quantity Y|   
|1 |Document1|2   | 
|2 |Document2|20  | 
|3 |Document3|5   | 
|4 |Document4|1   | 
|5 |Document5|22  |   

爲B項我定製FIFO功能結果:

|No|Name  |Quantity Y|   
|1 |Document100|2   | 
|2 |Document101|2   | 
|3 |Document102|4   | 

預期的結果:

表2

Item|Quantity X|Name  |Quantity Y| 
A |20  |Document1 |2   | 
A |20  |Document2 |18  | 
A |21  |Document2 |2   | 
A |21  |Document3 |5   | 
A |21  |Document4 |1   | 
A |21  |Document5 |13  | 
A |10  |Document5 |10  | 
B |3   |Document101|2   | 
B |3   |Document102|1   | 
B |4   |Document102|1   | 
B |4   |Document103|3   | 

我已經使用SQL Server 2008.如何用SQL實現這一目標?

+3

我不明白,每個表之間的關係.. – sagi

+1

那麼你的FIFO功能是什麼樣子?這個文檔數據從哪裏來? –

+0

您可能想使用['cross apply'](https://technet.microsoft.com/en-us/library/ms175156(v = sql.105).aspx) - 但我看不到數據如何加入向上。 – DaveShaw

回答

1

我剛剛在這裏得到了一個奇怪的答案:)請坐下來看看。

--I use cte's to show you a sample of how it wiil work 
--Here comes table with incoming docs 
;WITH table1 as (
SELECT * 
FROM (VALUES 
(1, 'A', 20),(2, 'A', 21),(3, 'A', 10),(4, 'B', 3),(5, 'B', 4) 
)AS t([No],Item,[Quantity X]) 
--Here comes table with outgoing item A 
), itemA AS (
SELECT * 
FROM (VALUES   
(1, 'Document1',2),(2, 'Document2',20),(3, 'Document3',5),(4, 'Document4',1),(5, 'Document5',22) 
)AS t([No], Name, [Quantity Y]) 
--Here we fraction each quantity for documents in 1, 
--so if quantity is 20 there will be 20 rows with 1 
), recT1 AS (
    SELECT [No], Item, [Quantity X], 1 as [level], 1 as Qty 
    FROM table1 
    WHERE Item = 'A' 
    UNION ALL 
    SELECT [No], Item, [Quantity X], [level] +1,1 
    FROM recT1 
    WHERE [level] < [Quantity X] 
--same to items 
), recA AS (
    SELECT [No], [Quantity Y], 1 as [level], 1 as Qty 
    FROM itemA 
    UNION ALL 
    SELECT [No], [Quantity Y], [level] +1,1 
    FROM recA 
    WHERE [level] < [Quantity Y] 
--here we add ROW_NUMBER not to lost order 
), finalT1 as (
    SELECT *, ROW_NUMBER() OVER (ORDER BY [No], [Level]) as rn 
    from recT1 
), finalA as (
    SELECT *, ROW_NUMBER() OVER (ORDER BY [No], [Level]) as rn 
    FROM recA 
) 
--final query! 
SELECT t.Item, 
     t.[Quantity X], 
     ia.Name, 
     CASE WHEN a.[level] > t.[level] THEN t.[level] ELSE a.[level] END as [Quantity Y] 
FROM finalT1 t 
INNER JOIN finalA a 
    ON t.rn = a.rn 
LEFT JOIN itemA ia 
    ON ia.[No] = a.[No] 
WHERE a.[level] = a.[Quantity Y] or t.[level] = t.[Quantity X] 

輸出:

Item Quantity X Name  Quantity Y 
A  20   Document1 2 
A  20   Document2 18 
A  21   Document2 2 
A  21   Document3 5 
A  21   Document4 1 
A  21   Document5 13 
A  10   Document5 9 

對於B

Item Quantity X Name  Quantity Y 
B  3   Document100 2 
B  3   Document101 1 
B  4   Document101 1 
B  4   Document102 3 
+0

它工作正常!十分感謝。我只添加子句'OPTION(maxrecursion 0)' – Najlepszak

+0

我的榮幸!沒有太多的數據 - 所以我忘了'OPTION(maxrecursion 0)':(如果它有助於免費上/接受我的答案! – gofr1