مشكلة استعلام SQL عند الترقية من SQL Server 2000 إلى SQL Server 2008 R2
-
26-09-2019 - |
سؤال
أقوم حاليًا بترقية خادم قاعدة البيانات من SQL Server 2000 إلى SQL Server 2008 R2. واحدة من استفساراتي المستخدمة لتستغرق تحت ثانية لتشغيلها وتستغرق الآن أكثر من 3 دقائق (الجري على آلة أسرع).
أعتقد أنني قد حددت المكان الذي يحدث فيه خطأ ولكن ليس سبب حدوث خطأ. هل يمكن لأي شخص أن يشرح ما هي المشكلة وكيف يمكنني حلها؟
الرمز المختصر هو كما يلي:
SET ANSI_NULLS ON
GO
SET QUOTED_IDENTIFIER ON
GO
...
FROM
Registrar reg
JOIN EnabledType et ON et.enabledTypeCode = reg.enabled
LEFT JOIN [Transaction] txn ON txn.registrarId = reg.registrarId
WHERE
txn.transactionid IS NULL OR
txn.transactionid IN
(
SELECT MAX(transactionid)
FROM [Transaction]
GROUP BY registrarid
)
أعتقد أن القضية موجودة على "txn.transactionid هو لاغ أو" خط. إذا قمت بإزالة هذا الشرط ، فإنه يتم تشغيله بأسرع ما كان عليه (أقل من ثانية) وإرجاع جميع السجلات مطروحًا منها الصفوف الثلاثة التي كان من شملها هذا البيان. إذا قمت بإزالة الجزء الثاني من أو البيان ، فإنه يعيد الصفوف الثلاثة التي أتوقعها في أقل من ثانية.
هل يمكن لأي شخص أن يوجهني في الاتجاه الصحيح لسبب حدوث ذلك وعندما يحدث هذا التغيير؟
شكرا كثيرا مسبقا
جوناثان
لقد قبلت حل Alex وأدرجت الإصدار الجديد من الرمز. يبدو أننا وجدنا 0.1 ٪ من الاستعلامات التي يعمل عليها Optimiser الجديدة أبطأ.
WITH txn AS (
SELECT registrarId, balance , ROW_NUMBER() OVER (PARTITION BY registrarid ORDER BY transactionid DESC) AS RowNum
FROM [Transaction]
)
SELECT
reg.registrarId,
reg.ianaId,
reg.registrarName,
reg.clientId,
reg.enabled,
ISNULL(txn.balance, 0.00) AS [balance],
reg.alertBalance,
reg.disableBalance,
et.enabledTypeName
FROM
Registrar reg
JOIN EnabledType et
ON et.enabledTypeCode = reg.enabled
LEFT JOIN txn
ON txn.registrarId = reg.registrarId
WHERE
ISNULL(txn.RowNum,1)=1
ORDER BY
registrarName ASC
المحلول
حاول إعادة هيكلة الاستعلام باستخدام CTE و ROW_Number ...
WITH txn AS (
SELECT registrarId, transactionid, ...
, ROW_NUMBER() OVER (PARTITION BY registrarid ORDER BY transactionid DESC) AS RowNum
FROM [Transaction]
)
SELECT
...
FROM
Registrar reg
JOIN EnabledType et ON et.enabledTypeCode = reg.enabled
LEFT JOIN txn ON txn.registrarId = reg.registrarId
AND txn.RowNum=1