2009-09-21 20 views
19

हम MySQL का एक छोटा बेंचमार्क कर रहे हैं जहां हम देखना चाहते हैं कि यह हमारे डेटा के लिए कैसे कार्य करता है।एकाधिक धागे से MySQL तक पहुंचने के लिए कैसे

उस परीक्षण का हिस्सा यह देखना है कि यह कैसे काम करता है जब एकाधिक समवर्ती धागे विभिन्न प्रश्नों के साथ सर्वर को हथियार देते हैं।

MySQL documentation (5.0) बहु थ्रेडेड ग्राहकों के बारे में वास्तव में स्पष्ट नहीं है। मुझे यह इंगित करना चाहिए कि मैं थ्रेड सुरक्षित लाइब्रेरी के खिलाफ लिंक करता हूं (libmysqlclient_r.so)

मैं तैयार बयान का उपयोग कर रहा हूं और दोनों पढ़ना (चयन) लिखना और लिखना (अद्यतन, INSERT, हटाएं)।

  • क्या मुझे प्रति थ्रेड एक कनेक्शन खोलना चाहिए? और यदि ऐसा है: मैं यह भी कैसे कर सकता हूं .. ऐसा लगता है कि mysql_real_connect() मूल डीबी हैंडल देता है जो मुझे mysql_init() कहा जाता है)
  • यदि नहीं: मैं कैसे सुनिश्चित कर सकता हूं कि mysql_affected_rows जैसे परिणाम और तरीके सही मूल्य लौटाते हैं अन्य धागे की कॉल के साथ टकराव करने के लिए (म्यूटेक्स/ताले काम कर सकते हैं, लेकिन यह गलत लगता है)

उत्तर

25

एक बड़े बड़े सी अनुप्रयोग के रखरखाव के रूप में जो MySQL कई धागे से कॉल करता है, मैं कह सकता हूं कि मुझे प्रत्येक थ्रेड में नया कनेक्शन बनाने में कोई समस्या नहीं है। कुछ चेतावनियां है कि मैं का सामना करना पड़ा:

  • संपादित करें: ऐसा लगता है यह गोली केवल संस्करण < 5.5 पर लागू होता है; this page for your appropriate version देखें: जैसा कि आप कहते हैं कि आप पहले से ही कर रहे हैं, libmysqlclient_r के खिलाफ लिंक करें।
  • कॉल mysql_library_init() (एक बार, main() से)। मल्टीथ्रेडेड वातावरण में उपयोग के बारे में दस्तावेज़ों को यह देखने के लिए पढ़ें कि यह आवश्यक क्यों है।
  • प्रत्येक धागे में mysql_init() का उपयोग करके एक नया MYSQL संरचना बनाएं। इसका आपके लिए mysql_thread_init() पर कॉल करने का दुष्प्रभाव है। प्रत्येक धागे के अंदर सामान्य रूप से mysql_real_connect(), इसके थ्रेड-विशिष्ट MYSQL संरचना के साथ।
  • यदि आप बहुत सारे धागे बना रहे/नष्ट कर रहे हैं, तो आप प्रत्येक थ्रेड के अंत में mysql_thread_end() का उपयोग करना चाहेंगे (main() के अंत में)। वैसे भी यह अच्छा अभ्यास है।

असल में, MYSQL structs या कि struct (अर्थात MYSQL_STMT रों) के लिए विशिष्ट बनाया कुछ भी हिस्सा नहीं है और यह अपेक्षा के अनुसार काम करेंगे।

यह मुझे कनेक्शन पूल बनाने से कम काम की तरह लगता है।

+1

यह वही उत्तर था जिसकी मुझे आवश्यकता थी। मुझे एहसास नहीं हुआ कि मुझे प्रत्येक थ्रेड में mysql_init को कॉल करना होगा - मैंने इसे मुख्य बार() में किया था। धन्यवाद –

+1

@chazomaticus, आप आम तौर पर कितने धागे का उपयोग करेंगे और आप कितने कनेक्शन खोलेंगे? क्या यह बड़े पैमाने पर धागे/कनेक्शन के पैमाने पर है? एक कनेक्शन पूल वास्तव में उपयोगी होता है यदि आपके पास बहुत सारे धागे हैं (100 के - 1000 के) लेकिन 1000 कनेक्शन खोलने के ऊपरी हिस्से को नहीं चाहते हैं (जो आपको अधिकतम_कनेक्शन के लिए डिफ़ॉल्ट रूप से अनुमति नहीं दे सकता है) आमतौर पर 100 पर सेट होता है)। यदि आपके पास कम संख्या में धागे हैं तो आपका दृष्टिकोण काम करेगा। कोड उदाहरण दिखाने के लिए मेरे द्वारा +1। – Glen

+1

चूंकि इसाक डीबी पर दबाव डालने की कोशिश कर रहा है, जितना संभव हो सके उतने धागे। मैंने बिना किसी मुद्दे के ~ 1000 चलाए हैं (यदि सभी धागे समस्याएं हैं, तो उनका अधिकांश समय 'मतदान()' में निष्क्रिय रहता है, इसलिए यह सीपीयू-गहन नहीं है जैसा कि आप सोच सकते हैं, हालांकि यह एक हिस्सा खा सकता है स्मृति की)। आप डिफ़ॉल्ट रूप से अधिकतम 100 पर कैपिंग अधिकतम_कनेक्शन के बारे में सही हैं, इसलिए अधिकतम तनाव के लिए, वांछित के रूप में। – chazomaticus

6

आप एक कनेक्शन पूल बना सकते हैं। कनेक्शन के लिए आवश्यक प्रत्येक थ्रेड पूल से मुक्त एक का अनुरोध कर सकता है। यदि कोई कनेक्शन उपलब्ध नहीं है तो आप या तो नया कनेक्शन जोड़कर पूल को ब्लॉक या बढ़ा सकते हैं। यहाँ एक तो सवाल यह है/जवाब देने के बारे में connection pools in C

EDIT2:: यहां नमूने के तौर पर एक लिंक है

(हालांकि यह जावा आधारित है)

संपादित एक लेख here समर्थक है और एक कनेक्शन पूल का विपक्ष का वर्णन नहीं है Connection Pool for MySQL सी ++ में लिखा गया है। (आप शायद गोटो बयान को नजरअंदाज करना चाहिए जब आप अपने खुद के लागू करते हैं।)

+0

अच्छा जवाब .. धन्यवाद। लेकिन मुझे अभी भी एक से अधिक कनेक्शन खोलने में समस्या है और आपके द्वारा लिंक किए गए नमूने में कोड का टुकड़ा गुम है .. मैंने आपको +1 दिया है लेकिन मैं इसे स्वीकार नहीं करना चाहता (अभी तक) क्योंकि यह मेरे हल नहीं करता है एकाधिक कनेक्शन खोलने में समस्या –

+0

लेकिन लेखों को साझा करने के लिए वास्तव में धन्यवाद ~ – yaobin

-1

MySQL Threaded Clients in C

यह कहा गया है कि mysql_real_connect() डिफ़ॉल्ट रूप से सुरक्षित थ्रेड नहीं है। क्लाइंट लाइब्रेरी को थ्रेडेड एक्सेस के लिए संकलित करने की आवश्यकता है।

+0

मैं libmysqlclient_r लाइब्रेरी का उपयोग कर रहा हूं, इसलिए मुझे लगता है कि इसमें सभी थ्रेड सुरक्षा चीजें संकलित हैं। बस सुनिश्चित करने के लिए, मैं सभी कनेक्शन सामग्री करने की कोशिश करूंगा धागे को फैलाने से पहले और देखें कि क्या –

1

mySQL डॉक्स से मेरे लिए स्पष्ट लगता है कि किसी भी विशिष्ट MYSQL संरचना बिना किसी कठिनाई के एक धागे में इस्तेमाल किया जा सकता है - एक साथ अलग धागे में ही MYSQL संरचना का उपयोग स्पष्ट रूप से आप बेहद अप्रत्याशित परिणाम देने के लिए जा रहा है राज्य के रूप में संग्रहीत किया जाता है MYSQL कनेक्शन के भीतर।

इस प्रकार या तो प्रति थ्रेड कनेक्शन बनाते हैं या उपरोक्त सुझाव के अनुसार कनेक्शन के पूल का उपयोग करते हैं और किसी भी प्रकार के म्यूटेक्स का उपयोग करके उस पूल तक पहुंच (यानी कनेक्शन को रिजर्व या रिलीज़ करते हैं) की सुरक्षा करते हैं।

+0

यह मदद करता है कि मुझे संदेह है .. बस कई कनेक्शन बनाने के तरीके को समझने की आवश्यकता है .. अभी यह काम नहीं कर सकता है –

+0

कभी इसके साथ कोई समस्या नहीं थी लेकिन मैं आमतौर पर नहीं इन पुस्तकालयों का उपयोग करें। मुझे लगता है कि आप अलग-अलग MYSQL संरचनाओं को आवंटित करने और इनिट को जोड़ने और कनेक्ट करने में सक्षम होना चाहिए। – Elemental

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