2011-01-29 5 views
1

記事のタイトルに基づいて記事を検索するストアドプロシージャがあります。しかし、記事を閲覧した回数を数える同じテーブルの列を増やす必要もあります。複数のルックアップなしでデータを返し、行を更新しますか?

できるだけ効率的になろうと、私は、このアプローチには、2つの可能な方法を参照:ターゲット行のPKを得るための1つのSELECTを実行

  1. を。その後、そのPKを使用してビューの数を増やし、最後にPKを使用して別のSELECTをクリックして記事データを返します。

  2. SELECTを1回実行すると、アプリケーションに記事データが返され、返されたPKを使用してデータベースをもう一度ラウンドトリップしてビュー数を増やします。

私は#1がかなり速いことを知っていますが、それは3つのルックアップです。 #2はデータベースへの2回のラウンドトリップが必要です。このタスクを最適化する方法はありませんか?

EDITフィードバックに基づいて、私は次のことを思いつきました。コメントや建設的な批評をありがとう。

DECLARE @Slug VARCHAR(250) -- Stored procedure argument 

-- declare @UpdatedArticle table variable 
DECLARE @UpdatedArticle TABLE 
(
    ArtID INT, 
    ArtUserID UNIQUEIDENTIFIER, 
    ArtSubcategoryID INT, 
    ArtTitle VARCHAR(250), 
    ArtHtml VARCHAR(MAX), 
    ArtDescription VARCHAR(350), 
    ArtKeywords VARCHAR(250), 
    ArtLicenseID VARCHAR(10), 
    ArtViews BIGINT, 
    ArtCreated DATETIME2(7), 
    ArtUpdated DATETIME2(7) 
); 

UPDATE Article 
    SET ArtViews = ArtViews + 1 
OUTPUT 
    INSERTED.ArtID, 
    INSERTED.ArtUserID, 
    inserted.ArtSubcategoryID, 
    INSERTED.ArtTitle, 
    INSERTED.ArtHtml, 
    INSERTED.ArtDescription, 
    INSERTED.ArtKeywords, 
    INSERTED.ArtLicenseID, 
    INSERTED.ArtViews, 
    INSERTED.ArtUpdated, 
    INSERTED.ArtCreated 
INTO @UpdatedArticle 
WHERE ArtSlugHash = CHECKSUM(@Slug) AND ArtSlug = @Slug AND ArtApproved = 1 

SELECT a.ArtID, a.ArtUserID, a.ArtTitle, a.ArtHtml, a.ArtDescription, a.ArtKeywords, a.ArtLicenseID, 
    l.licTitle, a.ArtViews, a.ArtCreated, a.ArtUpdated, s.SubID, s.SubTitle, c.CatID, c.CatTitle, 
    sec.SecID, sec.SecTitle, u.UsrDisplayName AS UserName 
    FROM @UpdatedArticle a 
    INNER JOIN Subcategory s ON a.ArtSubcategoryID = s.SubID 
    INNER JOIN Category c ON s.SubCatID = c.CatID 
    INNER JOIN [Section] sec ON c.CatSectionID = sec.SecID 
    INNER JOIN [User] u ON a.ArtUserID = u.UsrID 
    INNER JOIN License l ON a.ArtLicenseID = l.LicID 

答えて

2

は、ここで、単一のUPDATE文で、OUTPUT文(以降のSQL Server 2005)を使用した方法です。

IF OBJECT_ID ('Books', 'U') IS NOT NULL 
    DROP TABLE dbo.Books; 

CREATE TABLE dbo.Books 
(
    BookID int NOT NULL PRIMARY KEY, 
    BookTitle nvarchar(50) NOT NULL, 
    ModifiedDate datetime NOT NULL, 
    NumViews int not null CONSTRAINT DF_Numviews DEFAULT (0) 
); 

INSERT INTO dbo.Books 
    (BookID, BookTitle, ModifiedDate) 
VALUES 
    (106, 'abc', GETDATE()), 
    (107, 'Great Expectations', GETDATE()); 


-- declare @UpdateOutput1 table variable 
DECLARE @UpdateOutput1 table 
(
    BookID int, 
    BookTitle nvarchar(50), 
    ModifiedDate datetime, 
    NumViews int 
); 


-- >>>> here is the update of Numviews and the Fetch 
-- update Numviews in Books table, and retrive the row 
UPDATE Books 
SET 
    NumViews = NumViews + 1 
OUTPUT 
    INSERTED.BookID, 
    INSERTED.BookTitle, 
    INSERTED.ModifiedDate, 
    INSERTED.NumViews 
    INTO @UpdateOutput1 
WHERE BookID = 106 

-- view updated row in Books table 
SELECT * FROM Books; 

-- view output row in @UpdateOutput1 variable 
SELECT * FROM @UpdateOutput1; 
+0

おかげで、私はこれに慣れていませんでした。私は私の質問に追加した変更されたコードに関するコメントを感謝します。また、最初の条件に一致する行がないのに、何も見つからないことを確認したい場合はうまくいくようです。 –

+0

あなたはこれで私に大きな頭痛を救った。 –

関連する問題