2013-06-05 11 views
8

कई अवसरों पर मैं लघु-सर्किटिंग सूची समझ या जनरेटर अभिव्यक्तियों के लिए पायथन वाक्यविन्यास चाहता था।लघु-सर्किटिंग सूची समझ

my_list = [1, 2, 3, 'potato', 4, 5] 
[x for x in my_list if x != 'potato'] 

result = [] 
for element in my_list: 
    if element != 'potato': 
     result.append(element) 

वहाँ एक समझ जो कम सर्किट के लिए भाषा का में समर्थन नहीं है:

यहाँ एक सरल सूची समझ, और अजगर में लूप के लिए बराबर है। प्रस्तावित वाक्य रचना, और अजगर में लूप के लिए बराबर:

[x for x in my_list while x != 'potato'] 
# --> [1, 2, 3] 

result = [] 
for element in my_list: 
    if element != 'potato': 
     result.append(element) 
    else: 
     break 

यह अनंत दृश्यों सहित मनमाना iterables, साथ काम करना चाहिए, और अभिव्यक्ति वाक्य रचना जनरेटर के लिए लचीला होना। मैं list(itertools.takewhile(lambda x: x != 'potato'), my_list) एक विकल्प के रूप के बारे में पता कर रहा हूँ, लेकिन:

  • यह विशेष रूप से pythonic नहीं है - थोड़ी देर समझ
  • के रूप में कुशल या तेजी से एक CPython समझ के रूप में यह शायद नहीं हो सकता के रूप में के रूप में पढ़ने योग्य नहीं
  • यह आउटपुट को बदलने के लिए एक अतिरिक्त कदम की आवश्यकता होती है, जबकि इसे सीधे समझ में रखा जा सकता है, उदाहरण के लिए [x.lower() for x in mylist]
  • यहां तक ​​कि original author doesn't seem to like it much

मेरा प्रश्न है, वहाँ कारण है कि यह एक अच्छा विचार उपयोग के इस मामले को व्याकरण का विस्तार करने में नहीं है, या यह सिर्फ संभव नहीं है क्योंकि अजगर देव लगता है कि यह शायद ही कभी उपयोगी होगा के बारे में कोई सैद्धांतिक शिकन थी? यह भाषा के लिए एक सरल जोड़ और एक उपयोगी विशेषता की तरह लगता है, लेकिन शायद मैं कुछ छिपी हुई subtleties या जटिलताओं को देख रहा हूँ।

संबंधित: this और this

+2

'परिणाम = []; my_list में x के लिए कोई भी (x == 'आलू' या परिणाम .append (x)) '। हम्म ... नहीं, मुझे लगता है कि यह लेने से भी बदतर है :) –

+0

मुझे लगता है कि आपको [python-dev] में एक अच्छा जवाब मिलने की अधिक संभावना है (http://mail.python.org/mailman/listinfo/python- देव) मेलिंग सूची। – Elazar

+0

@gnibbler: आपने अभी 'फ़िल्टरफल्से' लागू किया है, ओपी पहले 'आलू' के बाद सभी संलग्नक को रोकना चाहता है। कोशिश करें: 'मिला = []; परिणाम = []; कोई भी (x == 'आलू' और नहीं मिला। अनुलग्नक (x) या result.append (x) यदि नहीं मिला तो my_list में x के लिए कोई नहीं) ' – PaulMcG

उत्तर

6

, बाहर बदल जाता है के रूप में @Paul McGuire बताया गया है, कि यह गुइडो द्वारा PEP 3142 और rejected में प्रस्तावित किया गया था:

मुझे नहीं पता था कि वहाँ के लिए एक पीईपी था । मैं इस प्रकार इसे अस्वीकार करता हूं। कोई बिंदु उस पर अधिक समय बर्बाद कर रहा है।

हालांकि, वह स्पष्टीकरण नहीं देता है। मेलिंग सूची में, यह के खिलाफ अंक में से कुछ हैं:।।

  • "[समझ रहे हैं] एक सावधानी से 1 नेस्ट किए गए बयान और एक भी अभिव्यक्ति के बीच 1 परिवर्तन के लिए बनाया गया लेकिन इस प्रस्ताव पर ध्यान नहीं देता और कहा कि टूट जाता है (here)। " यही है, while कीवर्ड स्पष्ट लूप में while के अनुरूप नहीं है - यह केवल break है।
  • "यह पाइथन सीखना कठिन बनाता है क्योंकि यह सीखने के लिए एक और चीज जोड़ता है।" (citated here)
  • यह जनरेटर अभिव्यक्तियों और सूची-समझ के बीच एक और अंतर जोड़ता है। ऐसा लगता है कि इस वाक्यविन्यास को सूची समझने के लिए भी सवाल से बाहर है।

मुझे लगता है कि सामान्य सूची समझ से एक बुनियादी अंतर यह है कि while निस्संदेह अनिवार्य है, घोषणात्मक नहीं है। यह निष्पादन के आदेश पर निर्भर करता है और निर्देश देता है, जिसे भाषा (AFAIK) द्वारा गारंटी नहीं दी जाती है।मुझे लगता है कि यही कारण है कि इसे हास्केल की समझ में शामिल नहीं किया गया है, जिसमें से पाइथन ने विचार चुरा लिया है।

बेशक, जेनरेटर अभिव्यक्तियों की दिशा होती है, लेकिन उनके तत्व प्रीकंप्यूटेड हो सकते हैं - फिर, AFAIK। पीईपी का उल्लेख है कि जेनरेटर एक्सप्रेशन के लिए केवल का प्रस्ताव दिया गया है - जो कुछ समझ में आता है।

बेशक, पायथन एक अनिवार्य भाषा है, लेकिन इससे समस्याएं बढ़ जाएंगी।

एक गैर-आदेशित संग्रह से बाहर निकलने के बारे में क्या?

[x for x in {1,2,3} while x!=2] 

आप इसे सरल for छोरों में भी नहीं है, लेकिन यह है कि कुछ आप भाषा के आधार पर लागू नहीं कर सकते है। takewhile इस प्रश्न का उत्तर देते हैं, लेकिन यह एक मनमाना जवाब है।


एक अंतिम बिंदु, ध्यान दें कि स्थिरता के लिए आप dropwhile के लिए समर्थन चाहते हैं। जैसे

[x for x in my_list from x != 'potato'] 

कुछ भी कम से संबंधित है जो बराबर for निर्माण करने के लिए, और इस बार यह संभवतः शॉर्ट सर्किट अगर my_list सिर्फ एक iterable है नहीं है।

+0

आप लूप संस्करण के लिए आसानी से लिख सकते हैं 'my_set में x के लिए: ...' यह कुछ भी उपयोगी करने के लिए ज्यादा समझ में नहीं आता है। –

+1

मुझे लगता है कि एक नया कीवर्ड शुरू किए बिना 'ड्रॉपफाई 'विकल्प की अनुपस्थिति (जैसे x [x के बाद x = x' आलू 'के बाद my_list में x के लिए x' x] =" मैं गोद लेने के बाधाओं में से एक रहा हूं, लेकिन मैं वास्तव में विचार की तरह - दुर्भाग्यवश, इसे पहले ही पीईपी 3142 (http://www.python.org/dev/peps/pep-3142/) के रूप में सबमिट कर दिया गया है और अस्वीकार कर दिया गया है। – PaulMcG

+0

@gnibbler मैंने इसे स्पष्ट रूप से संदर्भित किया है, हालांकि स्पष्ट रूप से नहीं: यह एक मनमाना जवाब है, जिसे भाषा से बेहतर ढंग से बचाया जा सकता है। 'लूप' लूप में इसे प्रतिबंधित करने का कोई वास्तविक तरीका नहीं है। – Elazar

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