SORU
24 Mart 2010, ÇARŞAMBA


SQL sorgu daha hızlı? Where Katılın kriterlere filtre ya?

Bu 2 sorgu karşılaştırın. Bu filtreyi koymak için daha hızlı kriterlerine katıl ya da madde vardı. Her zaman sonuç en kısa sürede anda ayarlamak azaltır, çünkü kriterleri katılmak daha hızlı olduğunu hissettim, ama emin değilim.

Görmek için bazı testler yaptıracağım, ama aynı zamanda daha nettir ki görüş almak için de okumak istedim.

Sorgu 1

SELECT      *
FROM        TableA a
INNER JOIN  TableXRef x
        ON  a.ID = x.TableAID
INNER JOIN  TableB b
        ON  x.TableBID = b.ID
WHERE       a.ID = 1            /* <-- Filter here? */

Sorgu 2

SELECT      *
FROM        TableA a
INNER JOIN  TableXRef x
        ON  a.ID = x.TableAID
        AND a.ID = 1            /* <-- Or filter here? */
INNER JOIN  TableB b
        ON  x.TableBID = b.ID

EDİT

Bir kaç test yaptım ve sonuçlar gerçekten çok yakın olduğunu gösteriyor, ancak WHERE maddesi aslında biraz daha hızlı! =)

Ben kesinlikle daha mantıklı WHERE yan filtreyi uygulamak için yapar katılıyorum, performans üzerindeki etkileri için merak ettim.

GEÇEN SÜRE ÖLÇÜT:Ms 143016
GEÇEN SÜRE KATILIN KRİTERLER:143256 ms

TEST

SET NOCOUNT ON;

DECLARE @num    INT,
        @iter   INT

SELECT  @num    = 1000, -- Number of records in TableA and TableB, the cross table is populated with a CROSS JOIN from A to B
        @iter   = 1000  -- Number of select iterations to perform

DECLARE @a TABLE (
        id INT
)

DECLARE @b TABLE (
        id INT
)

DECLARE @x TABLE (
        aid INT,
        bid INT
)

DECLARE @num_curr INT
SELECT  @num_curr = 1

WHILE (@num_curr <= @num)
BEGIN
    INSERT @a (id) SELECT @num_curr
    INSERT @b (id) SELECT @num_curr

    SELECT @num_curr = @num_curr   1
END

INSERT      @x (aid, bid)
SELECT      a.id,
            b.id
FROM        @a a
CROSS JOIN  @b b

/*
    TEST
*/
DECLARE @begin_where    DATETIME,
        @end_where      DATETIME,
        @count_where    INT,
        @begin_join     DATETIME,
        @end_join       DATETIME,
        @count_join     INT,
        @curr           INT,
        @aid            INT

DECLARE @temp TABLE (
        curr    INT,
        aid     INT,
        bid     INT
)

DELETE FROM @temp

SELECT  @curr   = 0,
        @aid    = 50

SELECT  @begin_where = CURRENT_TIMESTAMP
WHILE (@curr < @iter)
BEGIN
    INSERT      @temp (curr, aid, bid)
    SELECT      @curr,
                aid,
                bid
    FROM        @a a
    INNER JOIN  @x x
            ON  a.id = x.aid
    INNER JOIN  @b b
            ON  x.bid = b.id
    WHERE       a.id = @aid

    SELECT @curr = @curr   1
END
SELECT  @end_where = CURRENT_TIMESTAMP

SELECT  @count_where = COUNT(1) FROM @temp
DELETE FROM @temp

SELECT  @curr = 0
SELECT  @begin_join = CURRENT_TIMESTAMP
WHILE (@curr < @iter)
BEGIN
    INSERT      @temp (curr, aid, bid)
    SELECT      @curr,
                aid,
                bid
    FROM        @a a
    INNER JOIN  @x x
            ON  a.id = x.aid
            AND a.id = @aid
    INNER JOIN  @b b
            ON  x.bid = b.id

    SELECT @curr = @curr   1
END
SELECT  @end_join = CURRENT_TIMESTAMP

SELECT  @count_join = COUNT(1) FROM @temp
DELETE FROM @temp

SELECT  @count_where AS count_where,
        @count_join AS count_join,
        DATEDIFF(millisecond, @begin_where, @end_where) AS elapsed_where,
        DATEDIFF(millisecond, @begin_join, @end_join) AS elapsed_join

CEVAP
24 Mart 2010, ÇARŞAMBA


Performans açısından aynı (ve aynı planları yapılıyor

Mantıksal olarak, eğer hala LEFT JOIN INNER JOIN değiştirirseniz anlamı olduğunu işlem yapmak gerekir.

Bir çok durumda bu gibi görünecektir:

SELECT  *
FROM    TableA a
LEFT JOIN
        TableXRef x
ON      x.TableAID = a.ID
        AND a.ID = 1
LEFT JOIN
        TableB b
ON      x.TableBID = b.ID

ya da bu:

SELECT  *
FROM    TableA a
LEFT JOIN
        TableXRef x
ON      x.TableAID = a.ID
LEFT JOIN
        TableB b
ON      b.id = x.TableBID
WHERE   a.id = 1

Eski sorgu a.id için herhangi bir gerçek maçlar 1, ikinci sözdizimi (WHERE ile) mantıksal olarak daha uyumlu olması dışında iade etmeyecektir.

Bunu Paylaş:
  • Google+
  • E-Posta
Etiketler:

YORUMLAR

SPONSOR VİDEO

Rastgele Yazarlar

  • Murray Winiata

    Murray Winia

    2 ŞUBAT 2009
  • Semantic Mastery

    Semantic Mas

    30 EKİM 2013
  • YouplusmeVEVO

    YouplusmeVEV

    4 EYLÜL 2014