2016-11-30 2 views
1

私は在庫管理システムを発行しようとしています。発行日に製品を追跡する必要があります。だから私の条件がある - 店舗IDが1で、年が2014年である場合は、次のようにそれはその特定の年の発行日付に対してすべての製品を返す必要があります:私は、カレンダーのテーブルを使用しようとした左締結を使用してすべての日付を取得する

Product - Date - TotalIssued 
Keyboard - 2014-10-10 - 1 -- This product has been issued or given 1 time on that date of the year 2014 
Mouse - 2014-10-11 - 1 
Keyboard - 2014-10-12 - 0 
Mouse - 2014-10-12 - 0 
------------------------- 
------------------------- 
Keyboard - 2014-12-31 - 0 
Mouse - 2014-12-31 - 0 -- This will continue till the end of the year 

次のリンクを使用して1を作成しました:

Calendar Table

を私はカレンダーのテーブルを使用して所望の出力を得るために、次のクエリを使用しましたが、それは保存されている日付だけを意味する発行された製品のみを返します。 ReturnToStoreテーブル:

SELECT l.ItemName AS Product, m.PKDate AS Date, COUNT(m.PKDate) AS TotalIssued 
FROM [days] m 
LEFT JOIN ReturnToStore k ON CONVERT(DATE, k.IssuedDate) = m.PKDate 
LEFT JOIN Item l ON l.ItemID = k.ItemID 
WHERE m.calendar_year = 2014 AND k.StoreID = 1 
GROUP BY k.StoreID, l.ItemName, m.PKDate 

これは私が今取得しています出力されます。ここでは

Product - Date - TotalIssued 
Keyboard - 2014-10-10 - 1 
Mouse - 2014-10-11 - 1 

は、テーブル構造は以下のとおりです。

CREATE TABLE [dbo].[Item](
     [ItemID] [int] IDENTITY(1,1) NOT NULL, 
     [ItemName] [varchar](50) NULL, 
     [Description] [varchar](150) NULL, 
     [Tag] [varchar](50) NULL, 
    CONSTRAINT [PK_Item] PRIMARY KEY CLUSTERED 
    (
     [ItemID] ASC 
    ) 
    ) ON [PRIMARY] 

    INSERT INTO [dbo].[Item] 
       ([ItemName] 
       ,[Description] 
       ,[Tag]) 
     VALUES 
       ('Keyboard', 'IT Equipment', ''), 
       ('Mouse', 'IT Equipment', '') 

    CREATE TABLE [dbo].[ReturnToStore](
     [ID] [int] IDENTITY(1,1) NOT NULL, 
     [StoreID] [int] NULL, 
     [CategoryID] [int] NULL, 
     [ItemID] [int] NULL, 
     [Quantity] [float] NULL, 
     [IssuedDate] [datetime] NULL, 
     [Description] [varchar](150) NULL, 
     [OrderID] [varchar](50) NULL, 
    CONSTRAINT [PK_ReturnToStore] PRIMARY KEY CLUSTERED 
    (
     [ID] ASC 
    ) 
    ) ON [PRIMARY] 

    INSERT INTO [dbo].[ReturnToStore] 
       ([StoreID] 
       ,[CategoryID] 
       ,[ItemID] 
       ,[Quantity] 
       ,[IssuedDate] 
       ,[Description] 
       ,[OrderID]) 
     VALUES 
       (1, 1, 1, 10, '2014-10-10 00:00:00.000', '', 'PO-02'), 
       (1, 1, 2, 20, '2014-10-11 00:00:00.000', '', 'PO-03') 

**Note:** I guess, this could be done easily with LEFT JOIN using calendar table. But got stuck here. 

編集:私がきたように、私はポストを更新しました次のようにクエリをピボットに変換しました:

CREATE PROCEDURE [dbo].[MonthlyConsumption] 
@StoreID int, 
@Year int 

AS 

SELECT Distinct ItemName, 
    [1] AS M1, 
    [2] AS M2, 
    [3] AS M3, 
    [4] AS M4, 
    [5] AS M5, 
    [6] AS M6, 
    [7] AS M7, 
    [8] AS M8, 
    [9] AS M9, 
    [10] AS M10, 
    [11] AS M11, 
    [12] AS M12 
FROM 
(SELECT MONTH(m.PKDate) as YEAR, 
p.ItemName, k.IssuedDate, k.ItemID 
FROM [days] m 
CROSS JOIN (SELECT DISTINCT itemName,itemID FROM Item) p 
LEFT JOIN ReturnToStore k 
ON CONVERT(DATE, k.IssuedDate) = m.PKDate AND 
    p.itemid = k.itemid AND 
    k.StoreID = @StoreID 
LEFT JOIN Item l 
ON l.ItemID = k.ItemID 
WHERE m.calendar_year = @Year 
GROUP BY p.ItemName, m.PKDate, k.ItemID, k.IssuedDate) 

source 
PIVOT 
(
    COUNT(ItemID) 
    FOR YEAR 
    IN ([1], [2], [3], [4], [5], [6], [7], [8], [9], [10], [11], [12]) 
) AS PivotDay 

次の出力を返すこと:

SP_Pivot

それが繰り返していると私はその特定の日に何回も同じ製品の詳細を追加した場合、その後、ピボットに示す変化がない、なぜ私はわかりません与えられた出力と同じままです。

答えて

1

あなたの最初のエラーは、WHERE句の代わりに、ON句でLEFT JOINの右側のテーブルの上に条件を配置しているという事実です。

2つ目は、あなたもちょうど日付のように、項目名の派生テーブルを使用する必要があります。クエリが働い

SELECT p.ItemName AS Product, m.PKDate AS Date, COUNT(l.ItemID) AS TotalIssued 
FROM [days] m 
CROSS JOIN (SELECT DISTINCT itemName,itemID FROM Item) p 
LEFT JOIN ReturnToStore k 
ON CONVERT(DATE, k.IssuedDate) = m.PKDate AND 
    p.itemid = k.itemid AND 
    k.StoreID = 1 
LEFT JOIN Item l 
ON l.ItemID = k.ItemID 
WHERE m.calendar_year = 2014 
GROUP BY p.ItemName, m.PKDate 
+0

Worked but TotalIssued列の場合、常にすべての日付に対して1が表示されます。その年の特定の日付に製品が発行されていない場合、TotalIssued列は0になります。 –

+0

はい、右の表とは異なる列を数えます。今すぐ試す@ AT-2016 – sagi

+0

完璧に作業しました。ありがとう@sagi。 –

1

私はこれが解決策ですが、少なくともそれが改善されているかどうかわからないんだけど...

LEFT JOINは、真LEFT JOIN動作を取得するためにON句で右サイドテーブルの条件を置きます。 (WHEREに入ると、普通のINNER JOINの結果になります)。 move k.StoreID = 1ON句に:

SELECT l.ItemName AS Product, m.PKDate AS Date, COUNT(m.PKDate) AS TotalIssued 
FROM [days] m 
LEFT JOIN ReturnToStore k ON CONVERT(DATE, k.IssuedDate) = m.PKDate AND k.StoreID = 1 
LEFT JOIN Item l ON l.ItemID = k.ItemID 
WHERE m.calendar_year = 2014 
GROUP BY l.ItemName, m.PKDate 
+0

それが発行されていなかった日付の製品名が表示されませんTotalIssued列には、すべての日付に対して1が表示されます。 –

関連する問題