2011-01-03 16 views
22

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

+2

"अधिकांश स्ट्रिंग का उपभोग करने की आवश्यकता नहीं है"? इसका क्या मतलब है? स्ट्रिंग ऑब्जेक्ट मेमोरी में है, है ना? चूंकि यह सब स्मृति में है, और यह पहले से ही एक अनुक्रम है, पात्रों को फिर से शुरू करने के लिए कुछ भी आवश्यक नहीं है। क्या आप कृपया परिभाषित कर सकते हैं कि "अधिकांश स्ट्रिंग का उपभोग करने के लिए आवश्यक नहीं" से आपका क्या मतलब है? –

+0

हां, स्ट्रिंग पहले से ही स्मृति में है। लेकिन विभाजन के परिणामस्वरूप छिद्रण या सब्सट्रिंग बनाने के लिए मुझे पूरी स्ट्रिंग को पार करने की आवश्यकता नहीं है। –

+1

शायद आपको किसी प्रकार का टोकनिसर या स्कैनर चाहिए जो एक इटरेटर प्रदान करता है। नियमित अभिव्यक्ति समाधान के साथ नीचे जवाब काम कर सकता है। –

उत्तर

15

स्ट्रिंग को सीधे विभाजित नहीं करते हैं, लेकिन re मॉड्यूल में re.finditer() (और किसी भी संकलित नियमित अभिव्यक्ति पर संबंधित finditer() विधि) है।

@Zero एक उदाहरण के लिए पूछा:

>>> import re 
>>> s = "The quick brown\nfox" 
>>> for m in re.finditer('\S+', s): 
...  print(m.span(), m.group(0)) 
... 
(0, 3) The 
(4, 9) quick 
(13, 18) brown 
(19, 22) fox 
+2

स्प्लिट तारों को फिर से करने के लिए 're.finditer() 'का उपयोग करने का एक उदाहरण उपयोगी होगा। – Zero

+1

@ ज़ीरो, बिल्कुल कठिन नहीं, लेकिन यहां आप जाते हैं। – Duncan

5

S.Lott तरह, मैं काफी आप क्या चाहते हैं पता नहीं है।() अगले वर्ण को खोजने के लिए

s = "This is a string." 
for character in s: 
    print character 
for word in s.split(' '): 
    print word 

वहाँ भी कर रहे हैं और s.index s.find(): यहाँ कोड है कि मदद मिल सकती है है।


बाद में: ठीक है, ऐसा कुछ।

>>> def tokenizer(s, c): 
...  i = 0 
...  while True: 
...   try: 
...    j = s.index(c, i) 
...   except ValueError: 
...    yield s[i:] 
...    return 
...   yield s[i:j] 
...   i = j + 1 
... 
>>> for w in tokenizer(s, ' '): 
...  print w 
... 
This 
is 
a 
string. 
+1

टिप्पणियों में स्पष्टीकरण देखें। यह सवाल का जवाब नहीं देता है। – marcog

+0

वह स्पष्ट रूप से * अंतर्निहित * –

+3

@ 7vies के लिए भी पूछ रहा है: मैंने सोचा कि यह "नहीं" कहने से बेहतर था या कह रहा था "नियमित अभिव्यक्तियों का उपयोग करें (यानी ऊपर जवाब)।" – hughdbrown

0

आप SPARK की तरह कुछ (जो अजगर वितरण खुद में समाहित कर दिया गया है, हालांकि मानक पुस्तकालय से आयात योग्य नहीं) इस्तेमाल कर सकते हैं, लेकिन अंत में यह नियमित अभिव्यक्ति का उपयोग करता है और साथ ही इसलिए Duncan's answer संभवतः आप बस के रूप में अच्छी तरह से काम करेगा अगर यह "व्हाइटस्पेस पर विभाजित" के रूप में आसान था।

दूसरा, कहीं अधिक कठिन विकल्प सी में अपना पाइथन मॉड्यूल लिखना होगा यदि आप वास्तव में गति चाहते थे, लेकिन यह पाठ्यक्रम का एक बड़ा समय निवेश है।

3

यदि आपको पूरी स्ट्रिंग का उपभोग करने की आवश्यकता नहीं है, तो ऐसा इसलिए है क्योंकि आप कुछ विशिष्ट खोज रहे हैं, है ना? फिर बस उस के लिए देखें, re या .find() विभाजन के बजाय। इस तरह आप उस स्ट्रिंग का हिस्सा पा सकते हैं जिसमें आप रुचि रखते हैं, और उसे विभाजित करें।

+0

एप्लिकेशन में मुझे दिमाग में था, मैं सफेद जगह पर विभाजित करना चाहता था, तीसरा सबस्ट्रिंग जांचना था, जो कि था, चौथे या छठे सबस्ट्रिंग की जांच करें, और फिर संभवतः शेष स्ट्रिंग को संसाधित करें। –

+2

@pythonic रूपक: हाँ, अगर वह स्ट्रिंग * वास्तव में * लंबी है तो आप 're' या' find' का उपयोग करना चाहेंगे। दूसरे मामले में, बस इसे व्हाइटस्पेस पर विभाजित करें। मुझे नहीं पता, लेकिन मेरे लिए आपका प्रश्न लगता है जैसे यह समयपूर्व अनुकूलन हो सकता है। ;) तो आपको यह सुनिश्चित करने के लिए प्रोफाइल करना होगा। –

+3

@pythonic रूपक: सामान्य पाठ के लिए जो कि समयपूर्व अनुकूलन है। टेक्स्ट कहीं भी "बड़ा" होना शुरू होता है >> 10 एमबी। आपके द्वारा वर्णित एप्लिकेशन के लिए मैं पहले 6 शब्दों को प्राप्त करने के लिए 'text.split (कोई नहीं, 6)' के साथ जाऊंगा। अगर आपको पूरे पाठ को विभाजित करना है तो वैसे भी इसे अभी करें। –

0

itertools पर देखें। इसमें takewhile, islice और groupby जैसी चीजें शामिल हैं जो आपको एक पुनरावृत्ति को टुकड़ा करने की अनुमति देती हैं - एक स्ट्रिंग इटर्टेबल है - या तो इंडेक्स या बूलियन की स्थिति के आधार पर एक अन्य पुनरावर्तनीय में।

0

str.split का कोई अंतर्निहित इटरेटर-आधारित एनालॉग नहीं है। अपनी आवश्यकताओं पर निर्भर करता है आप एक सूची इटरेटर कर सकता है:

iterator = iter("abcdcba".split("b")) 
iterator 
# <list_iterator at 0x49159b0> 
next(iterator) 
# 'a' 

हालांकि, इस तीसरे पक्ष के पुस्तकालय से एक उपकरण संभावना है, आप क्या चाहते हैं प्रदान करता है more_itertools.split_at। उदाहरण के लिए this post भी देखें।

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