2013-02-12 50 views
13

मुझे सी # का उपयोग कर टेक्स्ट फ़ाइलों के समूह में एक स्ट्रिंग, लगभग 13 वर्णों की खोज करने की आवश्यकता है। टेक्स्ट फाइलों की संख्या बदल रही है और 100-1000 के बीच हो सकती है। फ़ाइलों का आकार 1 केबी और 10 एमबी के बीच हो सकता है।टेक्स्ट फ़ाइलों में स्ट्रिंग को खोजने का तेज़ तरीका

मैंने प्रत्येक फ़ाइल को खोलने के बेवकूफ तरीके की कोशिश की, इसे लाइन से लाइन पढ़ें और देखें कि स्ट्रिंग मौजूद है (index.of का उपयोग करके), लेकिन यह बहुत धीमी है। मैंने बॉयर-मूर एल्गोरिदम का उपयोग करने का भी प्रयास किया, जिसने 5 सेकंड तक समय में सुधार किया, लेकिन फिर भी यह धीमा लगता है।

खोज को गति देने के तरीके पर कोई विचार?

+2

आपकी मंदी शायद फाइल लाइन को लाइन से पढ़ने से आती है। एक बार सभी को स्मृति में एक फ़ाइल पढ़ें और उसे खोजें। – dda

+0

http://stackoverflow.com/questions/4289353/fastest-way-to-search-ascii-files-in-c-sharp-for-simple-keywords – Ofiris

+0

क्या आपको एक ही फाइल पर कई बार खोज करने की आवश्यकता है? – user626528

उत्तर

3

आपको सामग्री के साथ ऑपरेटिंग सिस्टम फ़ाइल खोज का उपयोग करने पर विचार करना चाहिए। Microsoft Windows Search 3.x SDK

पर एक नज़र डालें या आप फ़ाइलों की सरणी में खोज के लिए PLINQ का उपयोग कर सकते हैं।

File Content and Directory Search using Directory.GetFiles and PLINQ

+1

डाउनवॉटिंग नहीं, लेकिन मैं इसे समझ सकता हूं: आप केवल एक बेवकूफ समाधान (मूल रूप से इंडेक्सऑफ) बना रहे हैं जो पीआईएलक्यू के समानांतर है, जो इसे एक अच्छा समाधान नहीं बनाता है - आप मूल रूप से इसे और अधिक हार्डवेयर फेंक रहे हैं, जिससे इसे बनाते हैं और तेज। यह आदमी को कई फ़ाइलों में अपनी फ़ाइलों को पढ़ने और संसाधित करने की तरह कह रहा है। जैसा कि वह सुझाव देता है कि बॉयर-मूर का उपयोग करना इससे बेहतर है। इसके अलावा मुझे यकीन नहीं है कि क्या एमएस खोज कस्टम टोकननाइजेशन का समर्थन करता है, जो एक आवश्यकता प्रतीत होता है। तो, एक खोज विशेषज्ञ के रूप में मेरी राय में, आपके यहां से बेहतर उत्तर हैं। क्षमा करें ... मैं अच्छे इरादों की सराहना करता हूं। – atlaste

+0

शानदार! कि PLINQ फास्ट है! और बस कुछ लाइनें! मैंने इसके बजाय ReadAllText का उपयोग किया और यह सबसे तेज़ है। –

3

दो विकल्प दिमाग में आते हैं::

स्मृति में अपनी पाठ फ़ाइल को पढ़ने और सिर्फ एक ही बार में पूरी स्ट्रिंग खोज यह लिंक देखें।

यदि यह बहुत धीमी या बहुत याद आती है, तो अपाचे ल्यूसीन जैसे इंडेक्सर का उपयोग करें। वहाँ नेट के लिए उपलब्ध के लिए एक अच्छा और आसान एसडीके, Lucene.net

यहाँ कहा जाता है इसके लिए एक छोटा सा परिचय है: http://www.codeproject.com/Articles/29755/Introducing-Lucene-Net

1

आपके कंप्यूटर में यह स्मृति में सभी पाठ फ़ाइलों को लोड करने की कोशिश को संभाल सकता है (technique shown here का उपयोग करके और फिर स्मृति में पाठ का मूल्यांकन करें।

यदि आप एक ही समय में सभी फ़ाइलों को संभाल नहीं सकते हैं, तो इसे छोटी फ़ाइलों के लिए करें। फ़ाइल I/O आपका सबसे बड़ा खर्च होने वाला है, इसलिए आप चाहते हैं जितना संभव हो उतना कम करने के लिए।

8

हो पर निर्भर करता है कई बार आप 'खोज' करना चाहते हैं, आप एक खोज इंजन का उपयोग करना चाहते हैं या नहीं। यदि आप कई बार खोजना चाहते हैं, तो एक खोज इंजन का उपयोग करें, अन्यथा: नहीं। मैं वर्णन कर रहा हूं कि दोनों परिदृश्यों को कैसे कार्यान्वित किया जाए।

एक खोज इंजन का उपयोग करते समय: ऐसा लगता है कि आप सबस्ट्रिंग की तलाश में हैं, जिसका अर्थ है कि आपको अपनी पसंदीदा खोज इंजन का उपयोग करके अपनी फाइलों को इंडेक्स करना चाहिए, अधिमानतः आप अनुकूलित कर सकते हैं (ल्यूसीन, टेरियर, इत्यादि)। आपको जिस तकनीक की आवश्यकता है वह ट्रिगर को इंडेक्स करना है, यानी: सभी 3-वर्ण संयोजनों को अनुक्रमित करना होगा। एफएक्स .: 'foobar' 'foo', 'oob', 'oba' और 'bar' उत्पन्न करेगा। खोज करते समय, आप अपनी क्वेरी के साथ ऐसा करना चाहते हैं और इन सभी ट्रिग्राम के साथ एक खोज इंजन क्वेरी जारी करना चाहते हैं। (यह दस्तावेजों से पोस्टिंग सूचियों पर विलय-जुड़ाव चलाएगा, जो उनकी आईडी या जो भी आप पोस्टिंग सूचियों में डाल देंगे) वापस कर देंगे।

वैकल्पिक रूप से, आप प्रत्यय सरणी लागू कर सकते हैं और एक बार अपनी फाइलों को इंडेक्स कर सकते हैं। यदि आप शॉर्ट (1-2 चार) सबस्ट्रिंग्स खोजना चाहते हैं तो इससे थोड़ा अधिक लचीलापन मिलेगा, लेकिन इंडेक्स के संदर्भ में बनाए रखना मुश्किल है।

आप केवल कुछ ही बार खोज करने के लिए चाहते हैं, तो एल्गोरिथ्म का उपयोग करने के लिए या तो बोयर-मूर (मैं आमतौर पर बोयर-मूर-रविवार का उपयोग में वर्णित है (तेजी से अनुक्रमण प्रत्यय सरणियों के लिए CWI/एम्स्टर्डम में कुछ शोध भी नहीं है) [ग्राहम ए स्टीफन, स्ट्रिंग सर्च]) या एक संकलित डीएफए (आप उन्हें एनएफए से बना सकते हैं, जो बनाना आसान है)। हालांकि, यह आपको केवल एक छोटी गति वृद्धि देगा, सरल कारण यह है कि डिस्क आईओ शायद आपकी बाधा है और बाइट्स का एक गुच्छा की तुलना करना है जिसे आपको किसी भी तरह से डीकोड करने की आवश्यकता है।

सबसे बड़ा सुधार जो आप कर सकते हैं वह लाइन द्वारा आपकी फ़ाइल लाइन नहीं पढ़ रहा है, बल्कि ब्लॉक में। 64 KB के ब्लॉक आकार का उपयोग करने के लिए आपको NTFS को कॉन्फ़िगर करना चाहिए यदि आप 64 KB के गुणों में फ़ाइलों को पढ़ और पढ़ सकते हैं - एक ही पढ़ने में 4 एमबी या अधिक सोचें। मैं एसिंक्रोनस आईओ का उपयोग करने का सुझाव भी दूंगा ताकि आप एक ही समय में पढ़ और संसाधित कर सकें (पहले डेटा पढ़ सकते हैं)। यदि आप इसे सही तरीके से करते हैं, तो आपको पहले से ही अधिकांश आधुनिक हार्डवेयर पर 10 एमबी के लिए एक अलग-अलग कार्यान्वयन देना चाहिए।

अंतिम लेकिन कम से कम नहीं, जानकारी की पुनर्प्राप्ति के दौरान उपयोग की जाने वाली एक साफ चाल भी तेज़ संपीड़न एल्गोरिदम का उपयोग करके डेटा को संपीड़ित करने के लिए है। चूंकि डिस्क IO स्मृति/cpu संचालन से धीमा है, यह शायद भी मदद करेगा। Google का स्नैपी कंप्रेसर एक तेज संपीड़न एल्गोरिदम का एक अच्छा उदाहरण है।

1

आप सूची में जोड़े गए फ़ोल्डरों में दस्तावेज़ों की खोज के लिए Microsoft की अनुक्रमण सेवा का उपयोग कर सकते हैं। Here एक बहुत अच्छा लेख है जिसे आप उपयोगकर्ता को अपनी टेक्स्ट फाइलों को खोजने के लिए कर सकते हैं

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

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