سؤال

لدي طاولة كبيرة مع 1 مليون+ السجلات.للأسف الشخص الذي قام بإنشاء الجدول قررت وضع التمر في varchar(50) الحقل.

أنا بحاجة إلى القيام بسيطة مقارنة التاريخ -

datediff(dd, convert(datetime, lastUpdate, 100), getDate()) < 31

لكنه فشل في convert():

Conversion failed when converting datetime from character string.

يبدو أن هناك شيئا في هذا المجال أنه لا يحب, و لأن هناك الكثير من السجلات لا أستطيع أن أقول فقط من خلال النظر في ذلك.كيف يمكنني صحيح تطهير كامل حقل التاريخ حتى لا تفشل في convert()?هنا هو ما لدي الآن:

select count(*)
from MyTable
where
    isdate(lastUpdate) > 0
    and datediff(dd, convert(datetime, lastUpdate, 100), getDate()) < 31

@SQLMenace

أنا لست قلقا حول الأداء في هذه الحالة.هذا هو الذهاب إلى أن تكون مرة واحدة الاستعلام.تغيير الجدول إلى حقل التاريخ والوقت ليس خيارا.

@جون Limjap

لقد حاولت إضافة ثالثة حجة, ولا فرق.


@SQLMenace

المشكلة الأكثر احتمالا كيف يتم تخزين البيانات, هناك اثنين فقط من آمن الأشكال.ISO YYYYMMDD;ISO 8601 yyyy-mm-dd Thh:mm:ss:mmm (بدون مسافات)

لا isdate() تحقق من أن تأخذ الرعاية من هذا ؟

لا تحتاج إلى 100 ٪ من الدقة.أريد فقط أن تحصل على معظم السجلات التي هي من آخر 30 يوما.


@SQLMenace

select isdate('20080131') -- returns 1
select isdate('01312008') -- returns 0

@براين Schkerke

مكان القضية ISDATE داخل الدالة CONVERT ().

وذلك بفضل!التي فعلت ذلك.

هل كانت مفيدة؟

المحلول

مكان CASE و ISDATE داخل CONVERT() وظيفة.

SELECT COUNT(*) FROM MyTable
WHERE
    DATEDIFF(dd, CONVERT(DATETIME, CASE IsDate(lastUpdate)
        WHEN 1 THEN lastUpdate
        ELSE '12-30-1899'
    END), GetDate()) < 31

محل '12-30-1899' مع التاريخ الافتراضي من اختيارك.

نصائح أخرى

ماذا عن كتابة المؤشر إلى حلقة من خلال محتويات محاولة المدلى بها لكل الدخول ؟ عند حدوث خطأ ، إخراج المفتاح الأساسي أو غيرها من تحديد تفاصيل المشكلة قياسية.لا أستطيع التفكير في مجموعة على أساس طريقة للقيام بذلك.

ليس تماما setbased ولكن إذا كان فقط 3 صفوف من 1 مليون سيئة فإنه سيوفر لك الكثير من الوقت

select * into BadDates
from Yourtable
where isdate(lastUpdate) = 0

select * into GoodDates
from Yourtable
where isdate(lastUpdate) = 1

ثم مجرد إلقاء نظرة على BadDates الجدول إصلاح ذلك

على ISDATE() أن تأخذ الرعاية من الصفوف التي لم تكن مهيأ بشكل صحيح إذا كان في الواقع يجري تنفيذها أولا.ومع ذلك ، إذا كنت ننظر في خطة التنفيذ ربما ستجد أن DATEDIFF المسند يتم تطبيقها لأول وبالتالي يسبب الألم.

إذا كنت تستخدم SQL Server إدارة Studio ضرب CTRL+L لعرض المقدرة تنفيذ خطة استعلام معين.

تذكر SQL ليست لغة إجرائية و قصر الدائرة المنطق قد تعمل ولكن فقط إذا كنت حذرا في كيفية تطبيقه.

ماذا عن كتابة المؤشر إلى حلقة من خلال محتويات محاولة المدلى بها لكل الدخول ؟

عند حدوث خطأ ، إخراج المفتاح الأساسي أو غيرها من تحديد تفاصيل المشكلة قياسية.

لا أستطيع التفكير في مجموعة على أساس طريقة للقيام بذلك.

تحرير - آه نعم لقد نسيت ISDATE().بالتأكيد نهج أفضل من استخدام المؤشر.+1 SQLMenace.

في تحويل المكالمة ، تحتاج إلى تحديد الثالث أسلوب المعلمة مثلا شكل datetimes أن يتم تخزين varchar ، كما هو محدد في هذه الوثيقة: يلقي وتحويل (T-SQL)

طباعة السجلات.تعطي المطبوعة إلى الغبي الذي قرر استخدام varchar(50) ونطلب منهم أن تجد مشكلة تسجيل.

في المرة القادمة قد نرى وجهة اختيار نوع بيانات مناسبة.

المشكلة الأكثر احتمالا كيف يتم تخزين البيانات, هناك اثنين فقط من آمن صيغ

ISO YYYYMMDD

ISO 8601 yyyy-mm-dd Thh:mm:ss:mmm(بدون مسافات)

هذه سوف تعمل بغض النظر عن لغتك.

قد تحتاج إلى القيام به مجموعة DATEFORMAT YMD (أو أيا كان يتم تخزين البيانات كما) أن تجعل من العمل

لا isdate() التحقق من أن تأخذ الرعاية من هذا ؟

تشغيل هذا لنرى ماذا سيحدث

select isdate('20080131')
select isdate('01312008')

أنا متأكد من أن تغيير الجدول/عمود قد لا يكون خيارا بسبب أي إرث متطلبات النظام, ولكن هل فكرت في إنشاء طريقة عرض التي لديها تاريخ التحويل المنطق في بني ، إذا كنت تستخدم أحدث إصدار من sql, ثم ربما يمكنك حتى استخدام فهرسة الرأي ؟

أود أن أقترح تنظيف الفوضى وتغيير العمود التاريخ والوقت لأن فعل مثل هذه الاشياء

WHERE datediff(dd, convert(datetime, lastUpdate), getDate()) < 31

لا يمكن استخدام مؤشر وسيكون عدة مرات أبطأ مما إذا كان التاريخ والوقت كولوم ، ن و لم

where lastUpdate > getDate() -31

تحتاج أيضا إلى أن تأخذ في الاعتبار ساعات و ثواني طبعا

مرخصة بموجب: CC-BY-SA مع الإسناد
لا تنتمي إلى StackOverflow
scroll top