كيفية إنشاء طريقة عرض mssql للحصول على معلومات الحالة الأخيرة
-
03-07-2019 - |
سؤال
لنفترض أن لدي جدولين، أحدهما لسجلات الكائنات والآخر لسجلات الأنشطة المتعلقة بهذه الكائنات.
أقوم بإدخال سجل جديد في جدول النشاط هذا في كل مرة يتم فيها إدراج كائن أو تحديثه.
لإخبارها بطريقة بسيطة، افترض أن لدي أربعة حقول في جدول النشاط؛معرف الكائن والنوع والحالة والتاريخ.
عندما يكون الكائن على وشك التحديث، أخطط للحصول على الحالة الأخيرة للكائن والبحث عن التغييرات.إذا كان هناك فرق بين قيمة التحديث والقيمة السابقة، سأقوم بتعيين القيمة بإدخال جديد، وإلا سأضعها فارغة.لذلك، على سبيل المثال، في عملية التحديث، يقوم المستخدم فقط بتغيير قيمة حالة الكائن ولكنه يترك قيمة النوع كما هي، لذلك سأقوم بإدراج صف جديد بقيمة فارغة للنوع وقيمة جديدة للحالة.
SELECT * FROM Activity; oid type status date ----------------------------------------- 1 0 1 2009.03.05 17:58:07 1 null 2 2009.03.06 07:00:00 1 1 null 2009.03.07 20:18:07 1 3 null 2009.03.08 07:00:00
لذلك لا بد لي من إنشاء طريقة عرض تخبرني بالحالة الحالية لكائني مثل،
SELECT * FROM ObjectStateView Where oid = 1; oid type status date ----------------------------------------- 1 3 2 2009.03.08 07:00:00
كيف يمكنني تحقيق ذلك_؟
المحلول
وعلى افتراض التاريخ للعثور على أحدث سجل:
CREATE VIEW foo
AS
SELECT
A.oid,
(SELECT TOP 1 type FROM Activity At WHERE At.OID = A.oid AND At.Date <= MAX(A.date) AND type IS NOT NULL),
(SELECT TOP 1 status FROM Activity Ast WHERE Ast.OID = A.oid AND Ast.Date <= MAX(A.date) AND status IS NOT NULL),
MAX(A.date) AS date
FROM
Activity A
GO
وتحرير: إذا كنت ترغب في التسجيل (غير مجربة)
CREATE VIEW foo
AS
SELECT TOP 1
A.oid,
At.type,
Ast.status,
A.date
FROM
Activity A
LEFT JOIN
(SELECT TOP 1 oid, date, type FROM Activity WHERE type IS NOT NULL ORDER BY date DESC) At ON A.OID = At.oid
LEFT JOIN
(SELECT TOP 1 oid, date, status FROM Activity WHERE status IS NOT NULL ORDER BY date DESC) Ast ON A.OID = Ast.oid
ORDER BY date DESC
GO
وإذا قمت بإضافة هذا في وقت سابق:
وسيكون حجم أضعافا مضاعفة لأن لديك للمس الجدول 11 أوقات مختلفة.
والحل الأفضل هو للحفاظ على الطاولة "الحالي" والحفاظ عليه من خلال الزناد على النشاط.
نصائح أخرى
هل تعتبر استخدام وظيفة MAX ؟
select oid, type, status, MAX(date) as max_date
from ObjectStateView
where oid = 1
ولست متأكدا حقا لماذا كنت تريد القيم الخالية في هناك. يمكنك تتبع ما الذي تغير بين المدخلات من خلال مقارنة أحدث دخول إلى السابق. ثم الدولة الحالية للكائن هو أحدث دخول في الجدول. يمكنك تحديد ما إذا كان قد تغير كائن عن طريق إنشاء تجزئة الأجزاء من الكائن الذي تريد تعقب التغييرات وتخزين بأنه عمود إضافي.
القيم التاريخية:
وبما أنك تقوم بتتبع التغييرات، فقد ترغب في رؤية حالة الكائن تاريخيًا:
SELECT a.oid,
a.date,
a_type.type,
a_status.status
FROM Activity a
LEFT JOIN Activity a_type
ON a_type.oid = a.oid
AND a_type.date = (SELECT TOP 1 date FROM Activity WHERE oid = a.oid AND date <= a.date AND type IS NOT NULL ORDER BY date DESC)
LEFT JOIN Activity a_status
ON a_status.oid = a.oid
AND a_status.date = (SELECT TOP 1 date FROM Activity where oid = a.oid AND date <= a.date AND status IS NOT NULL ORDER BY date DESC)
والتي سوف تعود:
oid date type status
----------- ---------- ----------- -----------
1 2009-03-05 0 1
1 2009-03-06 0 2
1 2009-03-07 1 2
1 2009-03-08 3 2
اعتبارات الأداء:
من ناحية أخرى، إذا كان لديك أكثر من عدد قليل من الحقول، وكان الجدول كبيرًا، فسيصبح الأداء مشكلة.في هذه الحالة سيكون من المنطقي أيضًا تخزين/تخزين القيم بأكملها في جدول آخر MyDataHistory, ، والتي قد تحتوي على بيانات كما في الجدول الموضح أعلاه.ثم يعد تحديد الإصدار الحالي (الأحدث) أمرًا تافهًا باستخدام طريقة عرض SQL التي تقوم بتصفية الصف الأخير (صف واحد فقط) حسب المعرف والتاريخ.