2017-04-19 6 views
6

का उपयोग कर स्ट्रिंग की तरह अनुक्रमों के लिए परीक्षण कैसे करें कुछ समय के लिए, पायथन के पास Abstract Base Classes (प्रस्तावित रूप से PEP 3119 में प्रस्तावित किया गया है), विशेष रूप से कंटेनर प्रकारों के लिए, कस्टम को सामान्यीकृत करने वाले कोड को लिखना आसान बनाता है प्रकार के। उदाहरण के लिए,पायथन 3 की मानक लाइब्रेरी

from collections.abc import Sequence, Set 

if isinstance(x, Sequence): 
    # Handle lists, tuples, or custom objects that behave like lists 
elif isinstance(x, Set): 
    # Handle anything that behaves like a set 

'gotchas' है कि मुझे कुछ समय तक फिसल गया है में से एक है कि str, bytes है, और bytearray सभी को और अधिक स्पष्ट रूप से सूची की तरह वस्तुओं के लिए Sequence रों माना जाता है, इसके अलावा में:

from collections.abc import ByteString, Sequence 

s = 'hello' 
b = b'hello' 
ba = bytearray(b'hello') 
lst = [0, 1, 2] 
t = (0, 1, 2) 

islistlike = lambda x: isinstance(x, Sequence) 

list(map(islistlike, [s, b, ba, lst, t])) # -> [True, True, True, True, True] 

यह निश्चित रूप से समझ में आता है: आमतौर पर ये तीन प्रकार वर्णों (या बाइट्स) की सूचियों या tuples की तरह व्यवहार करते हैं। हालांकि, यह पूछने के लिए एक बहुत ही सामान्य उपयोग मामले की तरह लगता है, क्या यह ऑब्जेक्ट x दोनों सूची-जैसी और स्ट्रिंग जैसी नहीं है? ठीक सीधा है:

islistlike = lambda x: isinstance(x, Sequence) and not isinstance(x, (str, ByteString)) 

list(map(islistlike, [s, b, ba, lst, t])) # -> [False, False, False, True, True] 

लेकिन यह जैसे कि यह एक काफी आम पैटर्न है कि मुझे आश्चर्य है कि अगर मैं मानक पुस्तकालय में कुछ याद कर रहा हूँ होगा लगता है।

  • वहाँ पायथन के मानक पुस्तकालय में किसी भी abc ऐसी है कि islistlike = lambda x: isinstance(x, abc) ऊपर पिछले उदाहरण की तरह व्यवहार करेगा है?
  • क्या Sequence बनाम स्ट्रिंग-जैसी कंटेनर के आसपास कहीं भी कोई डिज़ाइन चर्चा है? (मैं मानक पुस्तकालय प्रलेखन या पीईपी 3119. में इस से संबंधित कुछ भी नहीं मिला है)
+0

1. जहां तक ​​मुझे पता है। 2. जैसा कि आप ध्यान देते हैं, * "स्ट्रिंग-जैसी कंटेनर" * * * अनुक्रम होते हैं, सिंगल-कैरेक्टर स्ट्रिंग्स/बाइट्स ('बाइटस्ट्रिंग' को 'अनुक्रम' प्राप्त होता है), इसलिए * "बनाम" * वास्तव में नहीं बनाता है समझ। कई मामलों में एक स्ट्रिंग को एक फ़ंक्शन या विधि के लिए पूरी तरह से वैध तर्क माना जाएगा जो अनुक्रम लेता है, इसलिए जब यह मामला नहीं है तो आपको स्पष्ट होना होगा। – jonrsharpe

+0

@jonrsharpe टिप्पणियों के लिए धन्यवाद! मैं तर्क दूंगा कि "* बनाम *" स्थिति के आधार पर उपयुक्त हो सकता है। अक्सर, मैं स्ट्रिंग्स (बाइट्स, इत्यादि) को एकल परमाणु डेटा बिंदुओं के रूप में सोच रहा हूं, और मैं जानना चाहता हूं, क्या मैं स्ट्रिंग-जैसी वस्तुओं की एक सूची-जैसी कंटेनर से निपट रहा हूं, या क्या मैं एक स्ट्रिंग-जैसे से निपट रहा हूं आइटम। एक जगह यह आता है कि एक नेस्टेड शब्दकोश को फ़्लैट करने के लिए एक पुनरावर्ती फ़ंक्शन का उपयोग कर रहा है, उदाहरण के लिए - रिकर्सिव फ़ंक्शन के अंदर आप आइटम के प्रकार पर प्रेषण करना चाहते हैं। – DGrady

उत्तर

1

नहीं, मानक पुस्तकालय में कुछ भी नहीं है आसानी से दृश्यों अन्य अनुक्रम प्रकार बनाम str और तरह के बीच bytes भेद करने के लिए है। यदि यह आपके कोड-बेस में आम है तो आप अपना खुद का रोल करना चाहेंगे।

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