2012-04-05 10 views
12

मैं an article का जिक्र कर रहा था जो LINQ से SQL क्वेरीज़ को गति देने पर केंद्रित है। उल्लेख की गई तकनीकों में से एक है "संकलित क्वेरी का उपयोग करें" और बताता है कि इसका उपयोग कैसे करें।LINQ से SQL के संकलन क्वेरी को प्रदर्शन में सुधार करता है

मैं संकलित प्रश्नों के प्रदर्शन में सुधार देखना चाहता था और इसलिए मैंने लेखक द्वारा प्रदान किए गए एक ही उदाहरण की कोशिश की। मैंने नॉर्थविंड डीबी को डाटाकॉन्टेक्स्ट के रूप में इस्तेमाल किया। मैंने सामान्य निष्पादन और संकलित निष्पादन की कोशिश की और उन्हें LINQ पीएडी पर जांच की।

सबसे पहले मैंने को के बिना CompileQuery का उपयोग कर क्वेरी निष्पादित करने का प्रयास किया। इसमें 2.065 सेकंड लगे।

var oo = from o in Orders 
    where o.OrderDetails.Any (p => p.UnitPrice > 100) 
    select o; 

oo.Dump ("Order items with unit price more than $100"); 

var oo1 = from o in Orders 
    where o.OrderDetails.Any (p => p.UnitPrice > 10) 
    select o; 

oo1.Dump ("Order items with unit price more than $10"); 

दूसरे, प्रश्नों साथ CompileQuery का उपयोग कर। इसमें 2.100 सेकेंड लगे।

var oo = CompiledQuery.Compile ((TypedDataContext dc, decimal unitPrice) =>  
    from o in Orders 
    where o.OrderDetails.Any (p => p.UnitPrice > unitPrice) 
    select o 
); 

oo (this, 100).Dump ("Order items with unit price more than $100"); 
oo (this, 10).Dump ("Order items with unit price more than $10"); 

कई बार उन्हें फिर से निष्पादित करने से पता चला कि दोनों दृष्टिकोणों द्वारा लिया गया समय लगभग समान है।

यहां हम प्रत्येक विधि के लिए केवल दो क्वेरी निष्पादन देखते हैं। मैंने उनमें से प्रत्येक के लिए 10 प्रश्न बनाने की कोशिश की। लेकिन दोनों ने लगभग 7 सेकंड पूरे किए।

क्या प्रश्नों को पूर्व-संकलित करने से वास्तव में प्रदर्शन में सुधार होता है? या क्या मैं इसे उपयोग की शर्तों में गलत कर रहा हूं?

आपके समय और विचार के लिए धन्यवाद।

संपादित करें: स्वीकार किए जाते हैं जवाब पढ़ने के बाद, पाठकों को भी this article जो अच्छी तरह से बताते हैं कि कैसे संकलित प्रश्नों के प्रदर्शन में सुधार के माध्यम से जाना चाहते हो सकता है।

उत्तर

10

मन में भालू एक LINQ क्वेरी कि विशेष रूप से महंगा हो सकता है के दो मुख्य टुकड़े देखते हैं कि:

  1. एक एसक्यूएल वक्तव्य में LINQ भाव संकलन।
  2. एसक्यूएल वक्तव्य चल रहा है और परिणाम

आपके मामले में पुन: प्राप्त करने के लिए, आप एक अपेक्षाकृत सरल प्रश्न हैं, और या तो एक बहुत ही धीमी गति डेटाबेस कनेक्शन, कुछ बहुत बड़े डेटा सेट, या तालिकाओं है कि एक में सूचीबद्ध नहीं हैं इस विशेष क्वेरी को चलाने के लिए इष्टतम तरीका। या शायद तीनों का एक संयोजन।

तो आपकी क्वेरी (शायद 10-50 मिलीसेकंड) के लिए एसक्यूएल का उत्पादन करने के लिए कितना समय लगता है, इसकी तुलना में दूसरा कदम इतना समय ले रहा है (~ 1000 एमएस) कि आप शायद ही अंतर को देख सकें।

आप महत्वपूर्ण सुधार देखना होगा अगर निम्न स्थितियों के सभी सही हैं:

  1. अपने LINQ क्वेरी जटिल है,
  2. आप अपने डेटाबेस के लिए एक तेजी से कनेक्शन है,
  3. SQL क्वेरी ही जल्दी से चलाता है उस डेटाबेस पर, और
  4. परिणाम सेट इतना छोटा है कि यह डेटाबेस से अपेक्षाकृत तेज़ी से स्थानांतरित हो जाता है।

प्रैक्टिस में, मेरे पास ऐसे प्रश्न हैं जो संकलन के लिए 500ms से ऊपर ले सकते हैं, लेकिन वास्तव में चलाने के लिए केवल कुछ मिलीसेकंड ही ले सकते हैं। ये आम तौर पर ऐसे मामले होते हैं जहां मैं प्रीकंपलिंग प्रश्नों पर ध्यान केंद्रित करता हूं।

एक अच्छा तरीका समय प्रदर्शन आप किस तरह के precompiled क्वेरी से उम्मीद कर सकते हैं लाभ से आगे पता करने के लिए समय के लिए दूसरा आपकी क्वेरी एक Stopwatch वस्तु का उपयोग करने का उदाहरण है, और फिर सीधे LINQPad का विश्लेषण करें एसक्यूएल उपयोग करते हुए उत्पन्न एसक्यूएल चलाने सुविधा। यदि SQL क्वेरी जल्दी से लौटती है लेकिन LINQ क्वेरी में काफी समय लगता है, तो यह precompiling के लिए एक अच्छा उम्मीदवार है।

+0

तो इसका मतलब है कि बड़े प्रश्नों के मामले में हम संकलन समय को निष्पादन समय को खत्म कर सकते हैं और फिर केवल दूसरे चरण (निष्पादन और परिणामों को पुनर्प्राप्त करने) के बारे में सोच सकते हैं – Marshal

+0

@Marshal: हाँ, यह विचार है। – StriplingWarrior

+0

बहुत बहुत धन्यवाद जेम्स। यह वास्तव में सहायक था। वैसे, मैं आपके ब्लॉग पढ़ने का भी आनंद लेता हूं;) – Marshal

 संबंधित मुद्दे

  • कोई संबंधित समस्या नहीं^_^