سؤال

لدي استعلام يشبه هذا:

select
id
, int1
, int2
, (select count(*) from big_table_with_millions_of_rows 
    where id between t.int1 and t.int2)
from myTable t
where
....

حدد هذا إرجاع صف واحد بالضبط. المعرف المستخدم في تحديد Inline هو عمود مفهرس (المفتاح الأساسي). إذا استبدلت t.int1 و t.int2 مع قيم Int1 / Int2 التي تم إرجاعها بواسطة هذا الصف الفردي، يكمل الاستعلام في ميلي ثانية. إذا قمت بتنفيذ الاستعلام على النحو الوارد أعلاه - مع مراجع إلى Int1 / Int2، يستغرق حوالي 10 دقائق. عندما أقوم بتشغيل Profiler وإلقاء نظرة على ما يحدث بالفعل، أرى أن 99٪ من الوقت في الوقت الذي يكون فيه المحرك مشغولا بإرجاع البيانات من الاستعلام المضمن. يبدو كما لو كان MySQL يعمل بالفعل

select ... from big_table_with_millions_of_rows 

قليلا من الاستعلام المضمنة مرة واحدة قبل تطبيق

where id between t.int1 and t.int2

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

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

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

المحلول

إذا لم يتم تحسين SPAQUERY المرتبطة جيدا، فجرب هذا الاستعلام:

select
  t.id
, t.int1
, t.int2
, count(*)
from myTable t
left outer join big_table_with_millions_of_rows b
  on (b.id between t.int1 and t.int2)
where
....
group by t.id

يجب أن تحسين أفضل بكثير.


سؤالك المحدث: يمين، MySQL ليس أكثر RDBMS تطورا في السوق من حيث التحسين. لا تفاجأ عندما لا يستطيع MySQL تحسين حالات الزاوية مثل هذا.

أنا من محبي Mysql لسهولة الاستخدام ومصدر مفتوحا وجميع تلك الأشياء الجيدة، ولكن الحقيقة هي أن منافسيها بعيدون عن MySQL من حيث التكنولوجيا. تحتوي كل RDBMS على بعض "البقع العمياء" ولكن يبدو أن MySQL أكبر.

تأكد أيضا من أنك تستخدم أحدث إصدار من MySQL. أنها تعمل على تحسين المحسن في كل إصدار، لذلك قد تحصل على نتائج أفضل مع إصدار أحدث.

نصائح أخرى

حاول تجنب الاستقرار المرتبط باستخدام الانضمام إذا كنت تستطيع.

شاهد هذا الفيديو الرائع على أداء MySQL موقع YouTube. وبعد انتقل إلى 31:00 دقيقة. يتحدث رئيس أنابيب جاي المتحدث عن تجنب التلقائي المرتبط.

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

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