2009-08-28 14 views
11

हमें विभिन्न प्रकार के संदेशों को पढ़ने और गिनने की आवश्यकता है/0 जी10 जीबी टेक्स्ट फ़ाइल पर कुछ आंकड़े चलाएं, उदाहरण के लिए FIX इंजन लॉग। हम पर्ल में लिनक्स, 32-बिट, 4 सीपीयू, इंटेल, कोडिंग का उपयोग करते हैं लेकिन भाषा वास्तव में कोई फर्क नहीं पड़ता।डिस्क से 10 जीबी फ़ाइल पढ़ने का सबसे तेज़ तरीका क्या है?

मुझे टिम ब्रै के WideFinder project में कुछ रोचक युक्तियां मिली हैं। हालांकि, हमने पाया है कि मेमोरी मैपिंग का उपयोग 32 बिट आर्किटेक्चर द्वारा स्वाभाविक रूप से सीमित है।

हम कई प्रक्रियाओं उपयोग करने की कोशिश, तेजी से काम करने के लिए अगर हम समानांतर 4 प्रक्रियाओं 4 सीपीयू पर उपयोग करने में फ़ाइल पर कार्रवाई लगती है। संदर्भ स्विचिंग की लागत के कारण बहु-थ्रेडिंग जोड़ना शायद धीमा हो जाता है। हमने को थ्रेड पूल के आकार को बदलने की कोशिश की, लेकिन यह अभी भी सरल बहु-प्रक्रिया संस्करण से धीमा है।

मेमोरी मैपिंग भाग बहुत स्थिर नहीं है, कभी-कभी 2 जीबी फ़ाइल पर 80 सेकंड और कभी-कभी 7 सेकेंड लेता है, शायद पेज दोष या वर्चुअल मेमोरी उपयोग से संबंधित कुछ। वैसे भी, एमएमएपी 32 बिट आर्किटेक्चर पर 4 जीबी से अधिक पैमाने पर स्केल नहीं कर सकता है।

हमने पर्ल के IPC::Mmap और Sys::Mmap को आजमाया। को मानचित्र-घटाकर भी देखा गया, लेकिन समस्या वास्तव में I/O बाध्य है, प्रसंस्करण स्वयं पर्याप्त तेज़ है।

तो हम बफरिंग आकार, प्रकार, आदि ट्यूनिंग द्वारा अनुकूलन बुनियादी आई/ओ की कोशिश करने का फैसला किया

कर सकते हैं किसी को जो एक मौजूदा परियोजना, जहां इस समस्या कुशलता से किसी भी भाषा/मंच में हल किया गया था के बारे में पता है एक उपयोगी लिंक को इंगित करें या एक दिशा का सुझाव दें?

+2

2 जी के लिए एक सीपीयू पर कच्चा प्रदर्शन क्या है? आपको शायद यह निर्धारित करने की आवश्यकता है कि I/O समस्या है या CPU कंप्यूटेशंस है या नहीं। – Cervo

+2

यदि आप वास्तव में डिस्क (आईओ) बाध्य हैं, तो सबसे अच्छा तरीका शायद तेजी से डिस्क, अधिक डिस्क (RAID0, RAID5, RAID10, आदि) या 64-बिट मशीन को फ़ाइल को स्टोर करने के लिए पर्याप्त मेमोरी के साथ खरीदना है एक राम डिस्क। कोई भी उचित एकल डिस्क 50 एमबी/सेकंड खींचने में सक्षम होना चाहिए; कई तेज़ डिस्क आपको कम से कम 300 एमबी/सेकंड तक धक्का देने में सक्षम होना चाहिए। – derobert

+1

मैं आपको Sys :: Mmap का उपयोग न करने की सलाह दूंगा लेकिन फ़ाइल-मानचित्र (बाद के दस्तावेज़ों में बताए गए कारणों के लिए)। किसी भी मामले में आप शायद आईपीसी :: एमएमएपी का उपयोग नहीं करना चाहते हैं। –

उत्तर

9

अधिकांश समय आप I/O को सीपीयू बाध्य नहीं करेंगे, इस प्रकार केवल सामान्य फ़ाइल I/O के माध्यम से इस फ़ाइल को पढ़ें और इसे एकल थ्रेड में संसाधित करें। जब तक आप साबित न करें कि आप अपने एकल सीपीयू काम से अधिक I/O कर सकते हैं, तो अपना समय और कुछ भी बर्बाद न करें। वैसे भी, आपको पूछना चाहिए: पृथ्वी पर क्यों एक विशाल फ़ाइल में है? पृथ्वी पर क्यों वे इसे उत्पन्न करते समय उचित तरीके से विभाजित नहीं करते हैं? यह परिमाण अधिक मूल्यवान काम होगा। फिर आप इसे अलग I/O चैनलों में डाल सकते हैं और अधिक CPU का उपयोग कर सकते हैं (यदि आप किसी प्रकार का RAID 0 या NAS या ...) का उपयोग नहीं करते हैं।

मापें, मान लें नहीं। प्रत्येक परीक्षण से पहले कैश फ्लश करना न भूलें। याद रखें कि धारावाहिक I/O यादृच्छिक से तीव्रता तीव्र है।

0

मैं एक परियोजना है जिसमें हम बड़ी फ़ाइलों पढ़ रहे थे याद करने लगते हैं, हमारे कार्यान्वयन बहु सूत्रण इस्तेमाल किया - मूल रूप से n * worker_threads फ़ाइल के incrementing ऑफसेट (0, chunk_size, 2xchunk_size, 3x chunk_size पर शुरू किया गया ... एन-1x chunk_size) और जानकारी के छोटे हिस्से पढ़ रहा था। मैं इसके लिए हमारी तर्क को बिल्कुल याद नहीं कर सकता क्योंकि कोई और पूरी चीज़ को निराश कर रहा था - मजदूर इसके लिए एकमात्र चीज नहीं थे, लेकिन यह मोटे तौर पर हमने यह कैसे किया।

आशा है कि यह मदद करता है

2

आप फ़ाइल स्ट्रीमिंग और किसी भी दिलचस्प परिणाम एक उच्च माध्यमिक फाइल करने के लिए को छान के बारे में सोचा है? (जब तक आपके पास एक प्रबंधित आकार फ़ाइल न हो तब तक दोहराएं)।

3
शायद

आपने पहले ही इस मंच धागा पढ़ा, लेकिन यदि नहीं:

http://www.perlmonks.org/?node_id=512221

यह पर्ल का उपयोग कर का वर्णन करता है यह पंक्ति-दर-पंक्ति करने के लिए, और उपयोगकर्ताओं को लगता है कि करने के लिए पर्ल काफी सक्षम है लगते हैं इसका

ओह, क्या RAID सरणी से फ़ाइल को संसाधित करना संभव है? यदि आपके पास कई प्रतिबिंबित डिस्क हैं, तो पढ़ने की गति में सुधार किया जा सकता है। डिस्क संसाधनों के लिए प्रतिस्पर्धा आपके एकाधिक-थ्रेड को काम करने का प्रयास नहीं कर सकती है।

शुभकामनाएं।

3

मेरी इच्छा है कि मैं आपकी फ़ाइल की सामग्री के बारे में और जान सकूं, लेकिन यह पाठ के अलावा अन्य नहीं जानता है, यह एक उत्कृष्ट MapReduce की तरह समस्या की तरह लगता है।

पीएस, किसी भी फ़ाइल का सबसे तेज़ पठन एक रैखिक पढ़ना है। cat file > /dev/null गति होना चाहिए कि फ़ाइल को पढ़ा जा सकता है।

+3

दरअसल; एक समान समस्या पर काम कर रहे मेरे सहयोगी फ़ाइल पढ़ने की गति में अन्य मुद्दों को ट्रैक करने के लिए बिल्ली से समय का उपयोग कर रहे थे। एनएफएस एक भयानक समय चूसना था। :( –

1

यदि आपके पास कंप्यूटर का नेटवर्क है, तो मूल रूप से 10 जी फ़ाइल को जितना संभव हो उतना क्लाइंट पीसी कॉपी करें, प्रत्येक क्लाइंट पीसी को फ़ाइल के ऑफसेट को पढ़ने के लिए प्राप्त करें। अतिरिक्त बोनस के लिए, वितरित पढ़ने के अलावा बहु थ्रेडिंग को लागू करने के लिए प्रत्येक पीसी प्राप्त करें।

+3

"समस्या वास्तव में आईओ बाध्य है" <--- अच्छी भाग्य फ़ाइल को डिस्क से तेज़ी से मशीन पर कॉपी करने से इसे पढ़ सकता है। – derobert

1

लाइन द्वारा लाइन पढ़ने, एक बार फ़ाइल को पार्स करें। परिणामों को एक सभ्य डेटाबेस में एक तालिका में रखें। जितनी चाहें उतनी क्वेरी चलाएं। नए आने वाले डेटा के साथ नियमित रूप से जानवर को खिलाओ।

यह समझें कि 10 जीबी फ़ाइल में हेरफेर करना, इसे (यहां तक ​​कि स्थानीय) नेटवर्क में स्थानांतरित करना, जटिल समाधानों की खोज करना आदि में समय लगता है।

+2

फ़ीड डेटाबेस और रन क्वेरी perl में सभी प्रोसेसिंग करने से अधिक समय ले सकते हैं। (यह मेरे अनुभव से है, यहां तक ​​कि आप थोक भार और MySQL का उपयोग करते हैं जो आप उपयोग कर सकते हैं सबसे तेज़ दृष्टिकोण में से एक है।) –

+1

एक बार आपके पास * सभ्य * डेटाबेस में डेटा हो जाने के बाद, आप जितनी चाहें उतनी क्वेरी चला सकते हैं (यहां तक ​​कि जिन्हें आप नहीं जानते थे कि आप दौड़ना चाहते थे) थोड़ी अतिरिक्त लागत के साथ। –

1

मेरे पास एक सहकर्मी है जिसने 64-बिट लिनक्स पर जाकर अपने FIX पढ़ने को बढ़ाया है। यदि यह कुछ सार्थक है, तो कुछ फैनसीयर हार्डवेयर प्राप्त करने के लिए थोड़ा सा नकद छोड़ दें।

4

यह सब इस बात पर निर्भर करता है कि आप किस तरह के प्रीप्रोसेसिंग कर सकते हैं और कब और कब। हमारे पास कुछ सिस्टमों पर, हम ऐसी बड़ी टेक्स्ट फ़ाइलों को gzip करते हैं, जिससे उन्हें अपने मूल आकार के 1/5 से 1/7 तक कम कर दिया जाता है। यह संभव बनाता है कि हमें इन फ़ाइलों को बनाने के कुछ घंटे बाद संसाधित करने की आवश्यकता नहीं है, और सृजन के समय हमारे पास मशीनों पर वास्तव में कोई अन्य भार नहीं है।

प्रोसेसिंग उन्हें ज़ेडैट उनफाइलों के फैशन में कम या ज्यादा किया जाता है। हमारे प्रोसेसिंग। (अच्छी तरह से यह एक कस्टम बनाया जेडटी के साथ यूनिक्स सॉकेट पर किया गया है)। यह डिस्क I/o समय के लिए cpu समय का व्यापार करता है, और हमारे सिस्टम के लिए अच्छी तरह से इसके लायक है। बहुत सारे चर हैं जो इसे किसी विशेष प्रणाली के लिए बहुत खराब डिजाइन कर सकते हैं।

1

हम्म, लेकिन सी में पढ़ने() कमांड के साथ क्या गलत है? आमतौर पर 2 जीबी की सीमा होती है, तो अनुक्रम में इसे 5 बार कॉल करें। यह काफी तेज़ होना चाहिए।

1

यदि आप I/O बाध्य हैं और आपकी फ़ाइल एक डिस्क पर है, तो ऐसा करने के लिए बहुत कुछ नहीं है। पूरी फ़ाइल में एक सीधा एकल-थ्रेडेड रैखिक स्कैन डिस्क के डेटा को प्राप्त करने का सबसे तेज़ तरीका है। बड़े बफर आकारों का उपयोग थोड़ा सा मदद कर सकता है।

यदि आप फ़ाइल के लेखक को कई डिस्क/मशीनों पर पट्टी करने के लिए राजी कर सकते हैं, तो आप पाठक को मल्टीथ्रेड करने के बारे में सोच सकते हैं (एक थ्रेड प्रति रीड हेड, प्रत्येक थ्रेड एक ही पट्टी से डेटा पढ़ने)।

0

यह समस्या में नहीं बताया गया है कि अनुक्रम वास्तव में मायने रखता है या नहीं।तो, फ़ाइल को बराबर भागों में विभाजित करें, प्रत्येक 1 जीबी कहें, और चूंकि आप एकाधिक सीपीयू का उपयोग कर रहे हैं, तो एकाधिक थ्रेड एक समस्या नहीं होगी, इसलिए अलग-अलग थ्रेड का उपयोग करके प्रत्येक फ़ाइल को पढ़ें, और क्षमता की रैम का उपयोग करें> 10 जीबी, फिर आपकी सभी सामग्री कई थ्रेड द्वारा पढ़ा रैम में संग्रहीत किया जाएगा।

1

जब से तुम ने कहा कि मंच और भाषा कोई फर्क नहीं पड़ता ...

आप एक स्थिर प्रदर्शन है कि जितनी जल्दी स्रोत माध्यम के लिए एक ही रास्ता मुझे पता है कि इस पर किया जा सकता है, की अनुमति देता है के रूप में चाहते हैं विंडोज़ गैर-ओएस-बफर्ड गठबंधन अनुक्रमिक पढ़ता है। आप शायद कुछ या तीन बफर के साथ कुछ जीबी/एस प्राप्त कर सकते हैं, इसके अलावा, किसी भी प्रतिलिपि से बचने के लिए आपको किसी रिंग बफर (एक लेखक, 1+ पाठकों) की आवश्यकता होती है। सटीक कार्यान्वयन ड्राइवर/एपीआई पर निर्भर करता है। यदि आईओ से निपटने वाले थ्रेड (कर्नेल और यूजरमोड दोनों में) पर चलने वाली कोई मेमोरी प्रतिलिपि है, तो जाहिर है कि बड़ा बफर कॉपी करना है, आईओ करने के बजाय उस पर अधिक समय बर्बाद हो गया है। तो इष्टतम बफर आकार फर्मवेयर और ड्राइवर पर निर्भर करता है। विंडोज़ पर अच्छे मूल्यों को डिस्क IO के लिए 32 KB के गुणक हैं। विंडोज़ फाइल बफरिंग, मेमोरी मैपिंग और वह सब चीजें ओवरहेड जोड़ती हैं। केवल तभी अच्छा है जब (या दोनों) यादृच्छिक पहुंच तरीके से एक ही डेटा के एकाधिक पढ़ते हैं। तो अनुक्रमिक रूप से एक बार बड़ी फ़ाइल पढ़ने के लिए, आप नहीं चाहते कि ओएस कुछ भी बफर करें या कोई भी memcpy करें। यदि सी # का उपयोग करते हुए मार्शलिंग के कारण ओएस में कॉल करने के लिए जुर्माना भी है, तो जब तक आप सी ++/सीएलआई का उपयोग नहीं करते हैं तो इंटरऑप कोड को ऑप्टिमाइज़ेशन की आवश्यकता हो सकती है।

कुछ लोग समस्याओं पर हार्डवेयर फेंकना पसंद करते हैं, लेकिन यदि आपके पास पैसे से अधिक समय है, तो कुछ परिस्थितियों में 1000 एंटरप्राइज़ मूल्य कंप्यूटरों की तुलना में एक उपभोक्ता स्तर कंप्यूटर पर 100-1000x बेहतर करने के लिए चीजों को अनुकूलित करना संभव है। इसका कारण यह है कि यदि प्रसंस्करण भी विलंबता संवेदनशील है, तो दो कोरों का उपयोग करने से परे जा रहा है शायद विलंबता जोड़ रहा है। यही कारण है कि ड्राइवर गीगाबाइट्स/एस को दबा सकते हैं जबकि एंटरप्राइज़ सॉफ़्टवेयर समाप्त होने तक मेगाबाइट्स/एस पर फंस जाता है। जो भी रिपोर्टिंग, बिजनेस लॉजिक और एंटरप्राइज़ सॉफ़्टवेयर संभवतः दो कोर उपभोक्ता सीपीयू पर गीगाबाइट्स/एस पर भी किया जा सकता है, यदि आपके जैसा लिखा गया है तो 80 के लेखन में एक गेम था। इस तरह से अपने पूरे व्यावसायिक तर्क के करीब आने वाले सबसे प्रसिद्ध उदाहरण एलएमएक्स विदेशी मुद्रा विनिमय है, जिसने अपने कुछ रिंग बफर आधारित कोड को प्रकाशित किया, जिसे नेटवर्क कार्ड ड्राइवरों द्वारा प्रेरित किया गया था।

सभी सिद्धांतों को भूलना, यदि आप < 1 जीबी/एस से खुश हैं, तो मुझे विंडोज़ पर एक संभावित प्रारंभिक बिंदु Winimage से readfile स्रोत को देख रहा है, जब तक आप एसडीके/ड्राइवर नमूने में खोदना नहीं चाहते। एसएसडी गति पर सही ढंग से perf की गणना करने के लिए इसे कुछ स्रोत कोड फ़िक्स की आवश्यकता हो सकती है। बफर आकार के साथ प्रयोग भी। स्विच/एच बहु-थ्रेडेड और/ओ ओवरलैप्ड (समापन बंदरगाह) IO इष्टतम बफर आकार (32,64,128 केबी आदि का प्रयास करें) के साथ आईओओ मेरे अनुभव में कोई विंडोज़ फाइल बफरिंग नहीं करते हैं, साथ ही साथ एसएसडी (ठंडा डेटा) से पढ़ते समय सर्वश्रेष्ठ perf देते हैं प्रसंस्करण (एडलर प्रसंस्करण के लिए/ए का उपयोग करें अन्यथा यह बहुत सीपीयू-बाध्य है)।

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

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